1.9.19.2139099/4.08.00.01
authorImagination Technologies/TI <imgtec>
Mon, 11 Feb 2013 22:34:31 +0000 (00:34 +0200)
committerGrazvydas Ignotas <notasas@gmail.com>
Mon, 11 Feb 2013 22:34:31 +0000 (00:34 +0200)
260 files changed:
GPL-COPYING [new file with mode: 0644]
INSTALL
MIT-COPYING [new file with mode: 0644]
Makefile
README
eurasiacon/build/linux2/bits.mk
eurasiacon/build/linux2/buildvars.mk
eurasiacon/build/linux2/commands.mk
eurasiacon/build/linux2/common/apis/xorg.mk
eurasiacon/build/linux2/common/dridrm.mk
eurasiacon/build/linux2/common/omap4.mk
eurasiacon/build/linux2/common/opencl.mk
eurasiacon/build/linux2/common/xorg.mk
eurasiacon/build/linux2/common/xorg_test.mk
eurasiacon/build/linux2/config/core.mk
eurasiacon/build/linux2/defs.mk
eurasiacon/build/linux2/kbuild/Makefile.template
eurasiacon/build/linux2/kbuild/external_tarball.mk
eurasiacon/build/linux2/kbuild/kbuild.mk
eurasiacon/build/linux2/kernel_module.mk
eurasiacon/build/linux2/kernel_version.mk
eurasiacon/build/linux2/moduledefs.mk
eurasiacon/build/linux2/modules.mk
eurasiacon/build/linux2/omap4430_linux/Makefile
eurasiacon/build/linux2/prepare_tree.mk
eurasiacon/build/linux2/this_makefile.mk
eurasiacon/build/linux2/tools/cc-check.sh
eurasiacon/build/linux2/toplevel.mk
include4/dbgdrvif.h
include4/img_defs.h
include4/img_types.h
include4/pdumpdefs.h
include4/pvr_debug.h
include4/pvrmodule.h
include4/pvrversion.h
include4/services.h
include4/servicesext.h
include4/sgx_options.h
include4/sgxapi_km.h
include4/sgxscript.h
services4/3rdparty/bufferclass_example/Kbuild.mk
services4/3rdparty/bufferclass_example/Linux.mk
services4/3rdparty/bufferclass_example/bufferclass_example.c
services4/3rdparty/bufferclass_example/bufferclass_example.h
services4/3rdparty/bufferclass_example/bufferclass_example_linux.c
services4/3rdparty/bufferclass_example/bufferclass_example_linux.h
services4/3rdparty/bufferclass_example/bufferclass_example_private.c
services4/3rdparty/bufferclass_example/bufferclass_example_private.h
services4/3rdparty/bufferclass_ti/bc_cat.c
services4/3rdparty/bufferclass_ti/bc_cat.h
services4/3rdparty/dc_omapfb3_linux/3rdparty_dc_drm_shared.h
services4/3rdparty/dc_omapfb3_linux/Kbuild.mk [new file with mode: 0644]
services4/3rdparty/dc_omapfb3_linux/Linux.mk [new file with mode: 0644]
services4/3rdparty/dc_omapfb3_linux/kbuild/Makefile [deleted file]
services4/3rdparty/dc_omapfb3_linux/makefile.linux.common [deleted file]
services4/3rdparty/dc_omapfb3_linux/omaplfb.h
services4/3rdparty/dc_omapfb3_linux/omaplfb_displayclass.c
services4/3rdparty/dc_omapfb3_linux/omaplfb_linux.c
services4/3rdparty/dc_ti335x_linux/3rdparty_dc_drm_shared.h
services4/3rdparty/dc_ti335x_linux/Kbuild.mk [new file with mode: 0644]
services4/3rdparty/dc_ti335x_linux/Linux.mk [new file with mode: 0644]
services4/3rdparty/dc_ti335x_linux/kbuild/Makefile [deleted file]
services4/3rdparty/dc_ti335x_linux/makefile.linux.common [deleted file]
services4/3rdparty/dc_ti335x_linux/omaplfb.h
services4/3rdparty/dc_ti335x_linux/omaplfb_displayclass.c
services4/3rdparty/dc_ti335x_linux/omaplfb_linux.c
services4/3rdparty/dc_ti81xx_linux/3rdparty_dc_drm_shared.h
services4/3rdparty/dc_ti81xx_linux/Kbuild
services4/3rdparty/dc_ti81xx_linux/Kbuild.mk [new file with mode: 0644]
services4/3rdparty/dc_ti81xx_linux/Linux.mk [new file with mode: 0644]
services4/3rdparty/dc_ti81xx_linux/kbuild/Makefile [deleted file]
services4/3rdparty/dc_ti81xx_linux/makefile.linux.common [deleted file]
services4/3rdparty/dc_ti81xx_linux/omaplfb.h
services4/3rdparty/dc_ti81xx_linux/omaplfb_displayclass.c
services4/3rdparty/dc_ti81xx_linux/omaplfb_linux.c
services4/3rdparty/linux_drm/Kbuild.mk
services4/3rdparty/linux_drm/Linux.mk
services4/3rdparty/linux_drm/ati_pcigart.c [deleted file]
services4/3rdparty/linux_drm/drm_agpsupport.c [deleted file]
services4/3rdparty/linux_drm/drm_auth.c [deleted file]
services4/3rdparty/linux_drm/drm_buffer.c [deleted file]
services4/3rdparty/linux_drm/drm_bufs.c [deleted file]
services4/3rdparty/linux_drm/drm_cache.c [deleted file]
services4/3rdparty/linux_drm/drm_context.c [deleted file]
services4/3rdparty/linux_drm/drm_crtc.c [deleted file]
services4/3rdparty/linux_drm/drm_crtc_helper.c [deleted file]
services4/3rdparty/linux_drm/drm_debugfs.c [deleted file]
services4/3rdparty/linux_drm/drm_dma.c [deleted file]
services4/3rdparty/linux_drm/drm_dp_i2c_helper.c [deleted file]
services4/3rdparty/linux_drm/drm_drv.c [deleted file]
services4/3rdparty/linux_drm/drm_edid.c [deleted file]
services4/3rdparty/linux_drm/drm_encoder_slave.c [deleted file]
services4/3rdparty/linux_drm/drm_fb_helper.c [deleted file]
services4/3rdparty/linux_drm/drm_fops.c [deleted file]
services4/3rdparty/linux_drm/drm_gem.c [deleted file]
services4/3rdparty/linux_drm/drm_global.c [deleted file]
services4/3rdparty/linux_drm/drm_hashtab.c [deleted file]
services4/3rdparty/linux_drm/drm_info.c [deleted file]
services4/3rdparty/linux_drm/drm_ioc32.c [deleted file]
services4/3rdparty/linux_drm/drm_ioctl.c [deleted file]
services4/3rdparty/linux_drm/drm_irq.c [deleted file]
services4/3rdparty/linux_drm/drm_lock.c [deleted file]
services4/3rdparty/linux_drm/drm_memory.c [deleted file]
services4/3rdparty/linux_drm/drm_mm.c [deleted file]
services4/3rdparty/linux_drm/drm_modes.c [deleted file]
services4/3rdparty/linux_drm/drm_pci.c [deleted file]
services4/3rdparty/linux_drm/drm_platform.c [deleted file]
services4/3rdparty/linux_drm/drm_proc.c [deleted file]
services4/3rdparty/linux_drm/drm_scatter.c [deleted file]
services4/3rdparty/linux_drm/drm_sman.c [deleted file]
services4/3rdparty/linux_drm/drm_stub.c [deleted file]
services4/3rdparty/linux_drm/drm_sysfs.c [deleted file]
services4/3rdparty/linux_drm/drm_trace_points.c [deleted file]
services4/3rdparty/linux_drm/drm_vm.c [deleted file]
services4/3rdparty/linux_drm/pvr_drm_mod.h
services4/3rdparty/linux_drm/pvr_drm_stubs.c
services4/include/env/linux/pvr_drm_shared.h
services4/include/kernelbuffer.h
services4/include/kerneldisplay.h
services4/include/pdump.h
services4/include/pvr_bridge.h
services4/include/pvr_bridge_km.h
services4/include/pvrmmap.h
services4/include/pvrsrv_errors.h
services4/include/servicesint.h
services4/include/sgx_bridge.h
services4/include/sgx_mkif_km.h
services4/include/sgx_ukernel_status_codes.h [new file with mode: 0644]
services4/include/sgxinfo.h
services4/srvkm/bridged/bridged_pvr_bridge.c
services4/srvkm/bridged/bridged_pvr_bridge.h
services4/srvkm/bridged/bridged_support.c
services4/srvkm/bridged/bridged_support.h
services4/srvkm/bridged/sgx/bridged_sgx_bridge.c
services4/srvkm/bridged/sgx/bridged_sgx_bridge.h
services4/srvkm/common/buffer_manager.c
services4/srvkm/common/deviceclass.c
services4/srvkm/common/deviceid.h
services4/srvkm/common/devicemem.c
services4/srvkm/common/handle.c
services4/srvkm/common/hash.c
services4/srvkm/common/lists.c
services4/srvkm/common/mem.c
services4/srvkm/common/mem_debug.c
services4/srvkm/common/metrics.c
services4/srvkm/common/osfunc_common.c
services4/srvkm/common/pdump_common.c
services4/srvkm/common/perproc.c
services4/srvkm/common/power.c
services4/srvkm/common/pvrsrv.c
services4/srvkm/common/queue.c
services4/srvkm/common/ra.c
services4/srvkm/common/refcount.c [new file with mode: 0644]
services4/srvkm/common/resman.c
services4/srvkm/devices/sgx/mmu.c
services4/srvkm/devices/sgx/mmu.h
services4/srvkm/devices/sgx/pb.c
services4/srvkm/devices/sgx/sgx_bridge_km.h
services4/srvkm/devices/sgx/sgxconfig.h
services4/srvkm/devices/sgx/sgxinfokm.h
services4/srvkm/devices/sgx/sgxinit.c
services4/srvkm/devices/sgx/sgxkick.c
services4/srvkm/devices/sgx/sgxpower.c
services4/srvkm/devices/sgx/sgxreset.c
services4/srvkm/devices/sgx/sgxtransfer.c
services4/srvkm/devices/sgx/sgxutils.c
services4/srvkm/devices/sgx/sgxutils.h
services4/srvkm/env/linux/Kbuild.mk
services4/srvkm/env/linux/Linux.mk
services4/srvkm/env/linux/env_data.h
services4/srvkm/env/linux/env_perproc.h
services4/srvkm/env/linux/event.c
services4/srvkm/env/linux/event.h
services4/srvkm/env/linux/linkage.h
services4/srvkm/env/linux/lock.h
services4/srvkm/env/linux/mm.c
services4/srvkm/env/linux/mm.h
services4/srvkm/env/linux/mmap.c
services4/srvkm/env/linux/mmap.h
services4/srvkm/env/linux/module.c
services4/srvkm/env/linux/mutex.c
services4/srvkm/env/linux/mutex.h
services4/srvkm/env/linux/mutils.c
services4/srvkm/env/linux/mutils.h
services4/srvkm/env/linux/osfunc.c
services4/srvkm/env/linux/osperproc.c
services4/srvkm/env/linux/pdump.c
services4/srvkm/env/linux/private_data.h
services4/srvkm/env/linux/proc.c
services4/srvkm/env/linux/proc.h
services4/srvkm/env/linux/pvr_bridge_k.c
services4/srvkm/env/linux/pvr_debug.c
services4/srvkm/env/linux/pvr_drm.c
services4/srvkm/env/linux/pvr_drm.h
services4/srvkm/env/linux/pvr_uaccess.h
services4/srvkm/hwdefs/ocpdefs.h
services4/srvkm/hwdefs/sgx530defs.h
services4/srvkm/hwdefs/sgx540defs.h
services4/srvkm/hwdefs/sgx544defs.h
services4/srvkm/hwdefs/sgxdefs.h
services4/srvkm/hwdefs/sgxerrata.h
services4/srvkm/hwdefs/sgxfeaturedefs.h
services4/srvkm/hwdefs/sgxmmu.h
services4/srvkm/hwdefs/sgxmpdefs.h
services4/srvkm/include/buffer_manager.h
services4/srvkm/include/device.h
services4/srvkm/include/handle.h
services4/srvkm/include/hash.h
services4/srvkm/include/lists.h
services4/srvkm/include/metrics.h
services4/srvkm/include/osfunc.h
services4/srvkm/include/osperproc.h
services4/srvkm/include/pdump_int.h
services4/srvkm/include/pdump_km.h
services4/srvkm/include/pdump_osfunc.h
services4/srvkm/include/perfkm.h [new file with mode: 0644]
services4/srvkm/include/perproc.h
services4/srvkm/include/power.h
services4/srvkm/include/queue.h
services4/srvkm/include/ra.h
services4/srvkm/include/refcount.h [new file with mode: 0644]
services4/srvkm/include/resman.h
services4/srvkm/include/services_headers.h
services4/srvkm/include/srvkm.h
services4/srvkm/include/ttrace.h
services4/srvkm/include/ttrace_common.h
services4/srvkm/include/ttrace_tokens.h
services4/system/include/syscommon.h
services4/system/omap3/sysconfig.c
services4/system/omap3630/sysconfig.c
services4/system/omap3630/sysinfo.h
services4/system/omap4/oemfuncs.h
services4/system/omap4/sysconfig.c
services4/system/omap4/sysconfig.h
services4/system/omap4/sysinfo.h
services4/system/omap4/syslocal.h
services4/system/omap4/sysutils.c
services4/system/omap4/sysutils_linux.c
services4/system/ti335x/sysconfig.c
services4/system/ti81xx/oemfuncs.h
services4/system/ti81xx/sysconfig.c
services4/system/ti81xx/sysconfig.h
services4/system/ti81xx/sysinfo.h
services4/system/ti81xx/syslocal.h
services4/system/ti81xx/sysutils.c
services4/system/ti81xx/sysutils_linux.c
services4/system/ti81xx/sysutils_linux_wqueue_compat.c [deleted file]
tools/intern/debug/client/linuxsrv.h
tools/intern/debug/dbgdriv/Kbuild.mk
tools/intern/debug/dbgdriv/Linux.mk
tools/intern/debug/dbgdriv/common/dbgdriv.c
tools/intern/debug/dbgdriv/common/dbgdriv.h
tools/intern/debug/dbgdriv/common/dbgdriv_ioctl.h
tools/intern/debug/dbgdriv/common/handle.c
tools/intern/debug/dbgdriv/common/hostfunc.h
tools/intern/debug/dbgdriv/common/hotkey.c
tools/intern/debug/dbgdriv/common/hotkey.h
tools/intern/debug/dbgdriv/common/ioctl.c
tools/intern/debug/dbgdriv/linux/hostfunc.c
tools/intern/debug/dbgdriv/linux/main.c

diff --git a/GPL-COPYING b/GPL-COPYING
new file mode 100644 (file)
index 0000000..83d1261
--- /dev/null
@@ -0,0 +1,344 @@
+-------------------------------------------------------------------------
+
+                   GNU GENERAL PUBLIC LICENSE
+                      Version 2, June 1991
+
+ Copyright (C) 1989, 1991 Free Software Foundation, Inc.
+    59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+                           Preamble
+
+  The licenses for most software are designed to take away your
+freedom to share and change it.  By contrast, the GNU General Public
+License is intended to guarantee your freedom to share and change free
+software--to make sure the software is free for all its users.  This
+General Public License applies to most of the Free Software
+Foundation's software and to any other program whose authors commit to
+using it.  (Some other Free Software Foundation software is covered by
+the GNU Library General Public License instead.)  You can apply it to
+your programs, too.
+
+  When we speak of free software, we are referring to freedom, not
+price.  Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+this service if you wish), that you receive source code or can get it
+if you want it, that you can change the software or use pieces of it
+in new free programs; and that you know you can do these things.
+
+  To protect your rights, we need to make restrictions that forbid
+anyone to deny you these rights or to ask you to surrender the rights.
+These restrictions translate to certain responsibilities for you if you
+distribute copies of the software, or if you modify it.
+
+  For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must give the recipients all the rights that
+you have.  You must make sure that they, too, receive or can get the
+source code.  And you must show them these terms so they know their
+rights.
+
+  We protect your rights with two steps: (1) copyright the software, and
+(2) offer you this license which gives you legal permission to copy,
+distribute and/or modify the software.
+
+  Also, for each author's protection and ours, we want to make certain
+that everyone understands that there is no warranty for this free
+software.  If the software is modified by someone else and passed on, we
+want its recipients to know that what they have is not the original, so
+that any problems introduced by others will not reflect on the original
+authors' reputations.
+
+  Finally, any free program is threatened constantly by software
+patents.  We wish to avoid the danger that redistributors of a free
+program will individually obtain patent licenses, in effect making the
+program proprietary.  To prevent this, we have made it clear that any
+patent must be licensed for everyone's free use or not licensed at all.
+
+  The precise terms and conditions for copying, distribution and
+modification follow.
+
+                   GNU GENERAL PUBLIC LICENSE
+   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
+
+  0. This License applies to any program or other work which contains
+a notice placed by the copyright holder saying it may be distributed
+under the terms of this General Public License.  The "Program", below,
+refers to any such program or work, and a "work based on the Program"
+means either the Program or any derivative work under copyright law:
+that is to say, a work containing the Program or a portion of it,
+either verbatim or with modifications and/or translated into another
+language.  (Hereinafter, translation is included without limitation in
+the term "modification".)  Each licensee is addressed as "you".
+
+Activities other than copying, distribution and modification are not
+covered by this License; they are outside its scope.  The act of
+running the Program is not restricted, and the output from the Program
+is covered only if its contents constitute a work based on the
+Program (independent of having been made by running the Program).
+Whether that is true depends on what the Program does.
+
+  1. You may copy and distribute verbatim copies of the Program's
+source code as you receive it, in any medium, provided that you
+conspicuously and appropriately publish on each copy an appropriate
+copyright notice and disclaimer of warranty; keep intact all the
+notices that refer to this License and to the absence of any warranty;
+and give any other recipients of the Program a copy of this License
+along with the Program.
+
+You may charge a fee for the physical act of transferring a copy, and
+you may at your option offer warranty protection in exchange for a fee.
+
+  2. You may modify your copy or copies of the Program or any portion
+of it, thus forming a work based on the Program, and copy and
+distribute such modifications or work under the terms of Section 1
+above, provided that you also meet all of these conditions:
+
+    a) You must cause the modified files to carry prominent notices
+    stating that you changed the files and the date of any change.
+
+    b) You must cause any work that you distribute or publish, that in
+    whole or in part contains or is derived from the Program or any
+    part thereof, to be licensed as a whole at no charge to all third
+    parties under the terms of this License.
+
+    c) If the modified program normally reads commands interactively
+    when run, you must cause it, when started running for such
+    interactive use in the most ordinary way, to print or display an
+    announcement including an appropriate copyright notice and a
+    notice that there is no warranty (or else, saying that you provide
+    a warranty) and that users may redistribute the program under
+    these conditions, and telling the user how to view a copy of this
+    License.  (Exception: if the Program itself is interactive but
+    does not normally print such an announcement, your work based on
+    the Program is not required to print an announcement.)
+
+These requirements apply to the modified work as a whole.  If
+identifiable sections of that work are not derived from the Program,
+and can be reasonably considered independent and separate works in
+themselves, then this License, and its terms, do not apply to those
+sections when you distribute them as separate works.  But when you
+distribute the same sections as part of a whole which is a work based
+on the Program, the distribution of the whole must be on the terms of
+this License, whose permissions for other licensees extend to the
+entire whole, and thus to each and every part regardless of who wrote it.
+
+Thus, it is not the intent of this section to claim rights or contest
+your rights to work written entirely by you; rather, the intent is to
+exercise the right to control the distribution of derivative or
+collective works based on the Program.
+
+In addition, mere aggregation of another work not based on the Program
+with the Program (or with a work based on the Program) on a volume of
+a storage or distribution medium does not bring the other work under
+the scope of this License.
+
+  3. You may copy and distribute the Program (or a work based on it,
+under Section 2) in object code or executable form under the terms of
+Sections 1 and 2 above provided that you also do one of the following:
+
+    a) Accompany it with the complete corresponding machine-readable
+    source code, which must be distributed under the terms of Sections
+    1 and 2 above on a medium customarily used for software interchange; or,
+
+    b) Accompany it with a written offer, valid for at least three
+    years, to give any third party, for a charge no more than your
+    cost of physically performing source distribution, a complete
+    machine-readable copy of the corresponding source code, to be
+    distributed under the terms of Sections 1 and 2 above on a medium
+    customarily used for software interchange; or,
+
+    c) Accompany it with the information you received as to the offer
+    to distribute corresponding source code.  (This alternative is
+    allowed only for noncommercial distribution and only if you
+    received the program in object code or executable form with such
+    an offer, in accord with Subsection b above.)
+
+The source code for a work means the preferred form of the work for
+making modifications to it.  For an executable work, complete source
+code means all the source code for all modules it contains, plus any
+associated interface definition files, plus the scripts used to
+control compilation and installation of the executable.  However, as a
+special exception, the source code distributed need not include
+anything that is normally distributed (in either source or binary
+form) with the major components (compiler, kernel, and so on) of the
+operating system on which the executable runs, unless that component
+itself accompanies the executable.
+
+If distribution of executable or object code is made by offering
+access to copy from a designated place, then offering equivalent
+access to copy the source code from the same place counts as
+distribution of the source code, even though third parties are not
+compelled to copy the source along with the object code.
+
+  4. You may not copy, modify, sublicense, or distribute the Program
+except as expressly provided under this License.  Any attempt
+otherwise to copy, modify, sublicense or distribute the Program is
+void, and will automatically terminate your rights under this License.
+However, parties who have received copies, or rights, from you under
+this License will not have their licenses terminated so long as such
+parties remain in full compliance.
+
+  5. You are not required to accept this License, since you have not
+signed it.  However, nothing else grants you permission to modify or
+distribute the Program or its derivative works.  These actions are
+prohibited by law if you do not accept this License.  Therefore, by
+modifying or distributing the Program (or any work based on the
+Program), you indicate your acceptance of this License to do so, and
+all its terms and conditions for copying, distributing or modifying
+the Program or works based on it.
+
+  6. Each time you redistribute the Program (or any work based on the
+Program), the recipient automatically receives a license from the
+original licensor to copy, distribute or modify the Program subject to
+these terms and conditions.  You may not impose any further
+restrictions on the recipients' exercise of the rights granted herein.
+You are not responsible for enforcing compliance by third parties to
+this License.
+
+  7. If, as a consequence of a court judgment or allegation of patent
+infringement or for any other reason (not limited to patent issues),
+conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License.  If you cannot
+distribute so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you
+may not distribute the Program at all.  For example, if a patent
+license would not permit royalty-free redistribution of the Program by
+all those who receive copies directly or indirectly through you, then
+the only way you could satisfy both it and this License would be to
+refrain entirely from distribution of the Program.
+
+If any portion of this section is held invalid or unenforceable under
+any particular circumstance, the balance of the section is intended to
+apply and the section as a whole is intended to apply in other
+circumstances.
+
+It is not the purpose of this section to induce you to infringe any
+patents or other property right claims or to contest validity of any
+such claims; this section has the sole purpose of protecting the
+integrity of the free software distribution system, which is
+implemented by public license practices.  Many people have made
+generous contributions to the wide range of software distributed
+through that system in reliance on consistent application of that
+system; it is up to the author/donor to decide if he or she is willing
+to distribute software through any other system and a licensee cannot
+impose that choice.
+
+This section is intended to make thoroughly clear what is believed to
+be a consequence of the rest of this License.
+
+  8. If the distribution and/or use of the Program is restricted in
+certain countries either by patents or by copyrighted interfaces, the
+original copyright holder who places the Program under this License
+may add an explicit geographical distribution limitation excluding
+those countries, so that distribution is permitted only in or among
+countries not thus excluded.  In such case, this License incorporates
+the limitation as if written in the body of this License.
+
+  9. The Free Software Foundation may publish revised and/or new versions
+of the General Public License from time to time.  Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+Each version is given a distinguishing version number.  If the Program
+specifies a version number of this License which applies to it and "any
+later version", you have the option of following the terms and conditions
+either of that version or of any later version published by the Free
+Software Foundation.  If the Program does not specify a version number of
+this License, you may choose any version ever published by the Free Software
+Foundation.
+
+  10. If you wish to incorporate parts of the Program into other free
+programs whose distribution conditions are different, write to the author
+to ask for permission.  For software which is copyrighted by the Free
+Software Foundation, write to the Free Software Foundation; we sometimes
+make exceptions for this.  Our decision will be guided by the two goals
+of preserving the free status of all derivatives of our free software and
+of promoting the sharing and reuse of software generally.
+
+                           NO WARRANTY
+
+  11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
+FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.  EXCEPT WHEN
+OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
+PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
+OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS
+TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU.  SHOULD THE
+PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
+REPAIR OR CORRECTION.
+
+  12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
+REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
+INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
+OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
+TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
+YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
+PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
+POSSIBILITY OF SUCH DAMAGES.
+
+                    END OF TERMS AND CONDITIONS
+
+       Appendix: How to Apply These Terms to Your New Programs
+
+  If you develop a new program, and you want it to be of the greatest
+possible use to the public, the best way to achieve this is to make it
+free software which everyone can redistribute and change under these terms.
+
+  To do so, attach the following notices to the program.  It is safest
+to attach them to the start of each source file to most effectively
+convey the exclusion of warranty; and each file should have at least
+the "copyright" line and a pointer to where the full notice is found.
+
+    <one line to give the program's name and a brief idea of what it does.>
+    Copyright (C) 19yy  <name of author>
+
+    This program is free software; you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation; either version 2 of the License, or
+    (at your option) any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with this program; if not, write to the Free Software
+    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+
+Also add information on how to contact you by electronic and paper mail.
+
+If the program is interactive, make it output a short notice like this
+when it starts in an interactive mode:
+
+    Gnomovision version 69, Copyright (C) 19yy name of author
+    Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+    This is free software, and you are welcome to redistribute it
+    under certain conditions; type `show c' for details.
+
+The hypothetical commands `show w' and `show c' should show the appropriate
+parts of the General Public License.  Of course, the commands you use may
+be called something other than `show w' and `show c'; they could even be
+mouse-clicks or menu items--whatever suits your program.
+
+You should also get your employer (if you work as a programmer) or your
+school, if any, to sign a "copyright disclaimer" for the program, if
+necessary.  Here is a sample; alter the names:
+
+  Yoyodyne, Inc., hereby disclaims all copyright interest in the program
+  `Gnomovision' (which makes passes at compilers) written by James Hacker.
+
+  <signature of Ty Coon>, 1 April 1989
+  Ty Coon, President of Vice
+
+This General Public License does not permit incorporating your program into
+proprietary programs.  If your program is a subroutine library, you may
+consider it more useful to permit linking proprietary applications with the
+library.  If this is what you want to do, use the GNU Library General
+Public License instead of this License.
+
+-------------------------------------------------------------------------
+
diff --git a/INSTALL b/INSTALL
index edba256..aefa6c3 100644 (file)
--- a/INSTALL
+++ b/INSTALL
@@ -4,43 +4,43 @@ Copyright (C) Imagination Technologies Ltd. All rights reserved.
 ======================================================================
 
 This file covers how to build and install the Imagination Technologies
-SGX DDK for the Linux kernel. 
+SGX DDK for the Linux kernel.
 
 
 Build System Environment Variables
 -------------------------------------------
 
-The SGX DDK Build scripts depend on a number of environment variables 
-being setup before compilation or installation of DDK software can 
+The SGX DDK Build scripts depend on a number of environment variables
+being setup before compilation or installation of DDK software can
 commence:
 
 $DISCIMAGE
-The DDK Build scripts install files to the location specified by the 
-DISCIMAGE environment variable, when the make install target is used. 
+The DDK Build scripts install files to the location specified by the
+DISCIMAGE environment variable, when the make install target is used.
 This should point to the target filesystem.
 $ export DISCIMAGE=/path/to/filesystem
 
 $KERNELDIR
-When building the SGX DDK kernel module, the build needs access 
-to the headers of the Linux kernel 
+When building the SGX DDK kernel module, the build needs access
+to the headers of the Linux kernel
 $ export KERNELDIR=/path/to/kernel
 
 $PATH
-If a cross compiler is being used make sure the PATH environment variable 
+If a cross compiler is being used make sure the PATH environment variable
 includes the path to the toolchain
 $ export PATH=$PATH:/path/to/toolchain
 
 $CROSS_COMPILE
-Since the SGX DDK Build scripts are geared toward a cross-compilation 
-workflow, the CROSS_COMPILE environment variable needs to be set 
+Since the SGX DDK Build scripts are geared toward a cross-compilation
+workflow, the CROSS_COMPILE environment variable needs to be set
 $ export CROSS_COMPILE=toolchain-prefix-
 
 
 Build and Install Instructions
 -------------------------------------------
 
-The SGX DDK configures different target builds within directories under 
-eurasiacon/build/linux/. 
+The SGX DDK configures different target builds within directories under
+eurasiacon/build/linux/.
 
 The supported build targets are:
 
@@ -49,12 +49,12 @@ The supported build targets are:
        clobber Removes all binaries for all builds as well.
        install Runs the install script generated by the build.
 
-The following variables may be set on the command line to influence a build. 
+The following variables may be set on the command line to influence a build.
 
-       BUILD   The type of build being performed. 
-                       Alternatives are release, timing or debug. 
-       CFLAGS  Build dependent optimisations and debug information flags.  
-       SILENT  Determines whether text of commands is produced during build.  
+       BUILD   The type of build being performed.
+                       Alternatives are release, timing or debug.
+       CFLAGS  Build dependent optimisations and debug information flags.
+       SILENT  Determines whether text of commands is produced during build.
 
 To build for, change to the appropriate target directory, e.g.:
 $ cd eurasiacon/build/linux/platform/kbuild
@@ -70,7 +70,3 @@ $ make install
 
 Become an ordinary user again:
 $ exit
-
-
-
-
diff --git a/MIT-COPYING b/MIT-COPYING
new file mode 100644 (file)
index 0000000..0cbd14e
--- /dev/null
@@ -0,0 +1,41 @@
+
+This software is Copyright (C) Imagination Technologies Ltd.
+
+You may use, distribute and copy this software under the terms of the MIT
+license displayed below.
+
+-----------------------------------------------------------------------------
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, this Software may be used under the terms of the GNU General
+Public License Version 2 ("GPL") in which case the provisions of GPL are
+applicable instead of those above.
+
+If you wish to allow use of your version of this Software only under the terms
+of GPL, and not to allow others to use your version of this file under the
+terms of the MIT license, indicate your decision by deleting from each file
+the provisions above and replace them with the notice and other provisions
+required by GPL as set out in the file called "GPL-COPYING" included in this
+distribution. If you do not delete the provisions above, a recipient may use
+your version of this file under the terms of either the MIT license or GPL.
+
+-----------------------------------------------------------------------------
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+-----------------------------------------------------------------------------
index 2daf6a9..ba1ce41 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -233,6 +233,7 @@ DISABLE_SGX_PB_GROW_SHRINK             ?= 1
 SUPPORT_LINUX_X86_PAT                  ?=1
 SUPPORT_LINUX_X86_WRITECOMBINE                 ?=1
 SUPPORT_SGX_LOW_LATENCY_SCHEDULING     ?=1
+SUPPORT_PVRSRV_GET_DC_SYSTEM_BUFFER    ?=1
 
 ifeq ($(SUPPORT_XORG),1)
 SUPPORT_PDUMP_MULTI_PROCESS = 1
@@ -293,6 +294,7 @@ SYS_CFLAGS.$(SUPPORT_BUFFER_CLASS)                  += -DSUPPORT_BUFFER_CLASS
 SYS_CFLAGS.$(SUPPORT_PERCONTEXT_PB)                    += -DSUPPORT_PERCONTEXT_PB 
 SYS_CFLAGS.$(SUPPORT_DYNAMIC_PBRESIZE)                 += -DSUPPORT_DYNAMIC_PBRESIZE
 SYS_CFLAGS.$(DISABLE_SGX_PB_GROW_SHRINK)        += -DDISABLE_SGX_PB_GROW_SHRINK
+SYS_CFLAGS.$(SUPPORT_PVRSRV_GET_DC_SYSTEM_BUFFER) += -DSUPPORT_PVRSRV_GET_DC_SYSTEM_BUFFER
 
 SYS_CFLAGS.$(USE_FBDEV)                                        += -DUSE_FBDEV
 SYS_CFLAGS.$(USE_FBDEV)                                        += -DFBDEV_NAME="\"$(FBDEV_NAME)\""
diff --git a/README b/README
index 8d31e51..2eae109 100644 (file)
--- a/README
+++ b/README
@@ -7,17 +7,18 @@ Copyright (C) Imagination Technologies Ltd. All rights reserved.
 About 
 -------------------------------------------
 
-This is the Imagination Technologies SGX DDK for the Linux kernel. 
+This is the Imagination Technologies SGX DDK for the Linux kernel.
 
 
 License
 -------------------------------------------
 
-You may use, distribute and copy this software under the terms of
-GNU General Public License version 2.
+You may use, distribute and copy this software under the terms of the MIT
+license.  Details of this license can be found in the file "MIT-COPYING".
 
-The full GNU General Public License version 2 is included in this 
-distribution in the file called "COPYING".
+Alternatively, you may use, distribute and copy this software under the terms
+of the GNU General Public License version 2.  The full GNU General Public
+License version 2 can be found in the file "GPL-COPYING".
 
 
 Build and Install Instructions
@@ -35,7 +36,7 @@ The DDK software must be installed by the root user.  Become the root user:
 $ su
 
 Install the DDK software:
-$ make install
+# make install
 
 Become an ordinary user again:
 $ exit
@@ -45,4 +46,4 @@ Contact information:
 -------------------------------------------
 
 Imagination Technologies Ltd. <gpl-support@imgtec.com>
-Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK
index 173e1ef..a1a7eef 100644 (file)
@@ -1,29 +1,43 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Title         Useful special targets which don't build anything
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
-
-# Useful special targets which don't build anything
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 ifneq ($(filter dumpvar-%,$(MAKECMDGOALS)),)
 dumpvar-%: ;
@@ -41,10 +55,8 @@ whatis-$(RELATIVE_OUT)/host/%: ;
 $(foreach _file_to_find,$(patsubst whatis-%,%,$(filter whatis-%,$(MAKECMDGOALS))),$(info $(strip $(foreach _m,$(ALL_MODULES),$(if $(filter $(_file_to_find),$(INTERNAL_TARGETS_FOR_$(_m))),$(_file_to_find) is in $(_m) which is defined in $(INTERNAL_MAKEFILE_FOR_MODULE_$(_m)),)))))
 endif
 
-.PHONY: ls-modules ls-modules-v
+.PHONY: ls-modules
 ls-modules:
-       @: $(foreach _m,$(ALL_MODULES),$(info $(_m)))
-ls-modules-v:
        @: $(foreach _m,$(ALL_MODULES),$(info $($(_m)_type) $(_m) $(patsubst $(TOP)/%,%,$(INTERNAL_MAKEFILE_FOR_MODULE_$(_m)))))
 
 ifeq ($(strip $(MAKECMDGOALS)),visualise)
@@ -64,18 +76,20 @@ endif
 .PHONY: help
 help:
        @echo 'Build targets'
-       @echo '  make, make build       Build the UM/KM components of the build and scripts'
-       @echo '  make components        Build only the UM components'
-       @echo '  make kbuild            Build only the KM components'
-       @echo '  make scripts           Build only the scripts (rc.pvr and install.sh)'
-       @echo '  make MODULE            Build the module MODULE and all its dependencies'
+       @echo '  make, make build       Build all components of the build'
+       @echo '  make components        Build only the user-mode components'
+       @echo '  make kbuild            Build only the kernel-mode components'
+       @echo '  make MODULE            Build the module MODULE and all of its dependencies'
        @echo '  make eurasiacon/binary2_.../target/libsomething.so'
        @echo '                         Build a particular file (including intermediates)'
        @echo 'Variables'
        @echo '  make V=1 ...           Print the commands that are executed'
+       @echo '  make W=1 ...           Enable extra compiler warnings'
+       @echo '  make D=opt ...         Set build system debug option (D=help for a list)'
        @echo '  make OUT=dir ...       Place output+intermediates in specified directory'
-       @echo '  make SOMEOPTION=1 ...  Set configuration options (see Makefile.config)'
-       @echo ''
+       @echo '  EXCLUDED_APIS=...      List of APIs to remove from the build'
+       @echo '  make SOMEOPTION=1 ...  Set configuration options (see config/core.mk)'
+       @echo '                         Defaults are set by $(PVR_BUILD_DIR)/Makefile'
        @echo 'Clean targets'
        @echo '  make clean             Remove only intermediates for the current build'
        @echo '  make clobber           As "make clean", but remove output files too'
@@ -84,4 +98,15 @@ help:
        @echo 'Special targets'
        @echo '  make whereis-MODULE    Show the path to the Linux.mk defining MODULE'
        @echo '  make whatis-FILE       Show which module builds an output FILE'
-       @echo '  make ls-modules[-v]    List all modules [with type+makefile]'
+       @echo '  make ls-modules        List all modules defined by makefiles'
+
+ifneq ($(filter help,$(D)),)
+empty :=
+space := $(empty) $(empty) 
+$(info Debug options)
+$(info $(space)D=modules                  dump module info)
+$(info $(space)D=freeze-config            prevent config changes)
+$(info $(space)D=config-changes           dump diffs when config changes)
+$(info Options may be combined: make D=freeze-config,config-changes)
+$(error D=help given)
+endif
index b6bd2d3..24fa829 100644 (file)
@@ -1,54 +1,66 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Title         Define global variables
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@Description   This file is read once at the start of the build, after reading 
+#               in config.mk. It should define the non-MODULE_* variables used 
+#               in commands, like ALL_CFLAGS
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
-
-#
-# This file is read once at the start of the build, after reading in
-# config.mk. It should define the non-MODULE_* variables used in commands,
-# like ALL_CFLAGS
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 ifeq ($(BUILD),debug)
-COMMON_FLAGS := -O0
+COMMON_USER_FLAGS := -O0
 else
 OPTIM ?= -O2
-COMMON_FLAGS := $(OPTIM)
+COMMON_USER_FLAGS := $(OPTIM)
 endif
 
 # FIXME: We should probably audit the driver for aliasing
 #
-COMMON_FLAGS += -fno-strict-aliasing
+COMMON_USER_FLAGS += -fno-strict-aliasing
 
 # We always enable debugging. Either the release binaries are stripped
 # and the symbols put in the symbolpackage, or we're building debug.
 #
-COMMON_FLAGS += -g
+COMMON_USER_FLAGS += -g
 
 # These flags are used for kernel, User C and User C++
 #
-COMMON_FLAGS += \
- -W -Wall -Wno-missing-field-initializers -Wmissing-format-attribute
+COMMON_FLAGS = -W -Wall
 
 # Some GCC warnings are C only, so we must mask them from C++
 #
@@ -56,11 +68,16 @@ COMMON_CFLAGS := $(COMMON_FLAGS) \
  -Wdeclaration-after-statement -Wno-format-zero-length \
  -Wmissing-prototypes -Wstrict-prototypes
 
-# If we saw W=1, turn on some extra warnings.
-# Most of these flags are new, so cc-option check them.
+# Additional warnings, and optional warnings.
 #
+WARNING_CFLAGS := \
+ -Wpointer-arith -Wunused-parameter \
+ -Wmissing-format-attribute \
+ $(call cc-option,-Wno-missing-field-initializers) \
+ $(call cc-option,-fdiagnostics-show-option)
+
 ifeq ($(W),1)
-COMMON_CFLAGS += \
+WARNING_CFLAGS += \
  $(call cc-option,-Wbad-function-cast) \
  $(call cc-option,-Wcast-qual) \
  $(call cc-option,-Wcast-align) \
@@ -82,18 +99,84 @@ COMMON_CFLAGS += \
  $(call cc-option,-Wwrite-strings)
 endif
 
+WARNING_CFLAGS += \
+ $(call cc-optional-warning,-Wunused-but-set-variable)
+
+HOST_WARNING_CFLAGS := \
+ -Wpointer-arith -Wunused-parameter \
+ -Wmissing-format-attribute \
+ $(call host-cc-option,-Wno-missing-field-initializers) \
+ $(call host-cc-option,-fdiagnostics-show-option)
+
+ifeq ($(W),1)
+HOST_WARNING_CFLAGS += \
+ $(call host-cc-option,-Wbad-function-cast) \
+ $(call host-cc-option,-Wcast-qual) \
+ $(call host-cc-option,-Wcast-align) \
+ $(call host-cc-option,-Wconversion) \
+ $(call host-cc-option,-Wdisabled-optimization) \
+ $(call host-cc-option,-Wlogical-op) \
+ $(call host-cc-option,-Wmissing-declarations) \
+ $(call host-cc-option,-Wmissing-include-dirs) \
+ $(call host-cc-option,-Wnested-externs) \
+ $(call host-cc-option,-Wold-style-definition) \
+ $(call host-cc-option,-Woverlength-strings) \
+ $(call host-cc-option,-Wpacked) \
+ $(call host-cc-option,-Wpacked-bitfield-compat) \
+ $(call host-cc-option,-Wpadded) \
+ $(call host-cc-option,-Wredundant-decls) \
+ $(call host-cc-option,-Wshadow) \
+ $(call host-cc-option,-Wswitch-default) \
+ $(call host-cc-option,-Wvla) \
+ $(call host-cc-option,-Wwrite-strings)
+endif
+
+HOST_WARNING_CFLAGS += \
+ $(call host-cc-optional-warning,-Wunused-but-set-variable)
+
+KBUILD_WARNING_CFLAGS := \
+ -Wno-unused-parameter -Wno-sign-compare
+KBUILD_WARNING_CFLAGS += \
+ $(call kernel-cc-optional-warning,-Wbad-function-cast) \
+ $(call kernel-cc-optional-warning,-Wcast-qual) \
+ $(call kernel-cc-optional-warning,-Wcast-align) \
+ $(call kernel-cc-optional-warning,-Wconversion) \
+ $(call kernel-cc-optional-warning,-Wdisabled-optimization) \
+ $(call kernel-cc-optional-warning,-Wlogical-op) \
+ $(call kernel-cc-optional-warning,-Wmissing-declarations) \
+ $(call kernel-cc-optional-warning,-Wmissing-include-dirs) \
+ $(call kernel-cc-optional-warning,-Wnested-externs) \
+ $(call kernel-cc-optional-warning,-Wno-missing-field-initializers) \
+ $(call kernel-cc-optional-warning,-Wold-style-definition) \
+ $(call kernel-cc-optional-warning,-Woverlength-strings) \
+ $(call kernel-cc-optional-warning,-Wpacked) \
+ $(call kernel-cc-optional-warning,-Wpacked-bitfield-compat) \
+ $(call kernel-cc-optional-warning,-Wpadded) \
+ $(call kernel-cc-optional-warning,-Wredundant-decls) \
+ $(call kernel-cc-optional-warning,-Wshadow) \
+ $(call kernel-cc-optional-warning,-Wswitch-default) \
+ $(call kernel-cc-optional-warning,-Wvla) \
+ $(call kernel-cc-optional-warning,-Wwrite-strings)
+
 # User C only
 #
 ALL_CFLAGS := \
- $(COMMON_CFLAGS) -Wpointer-arith -Wunused-parameter $(SYS_CFLAGS)
+ $(COMMON_USER_FLAGS) $(COMMON_CFLAGS) $(WARNING_CFLAGS) \
+ $(SYS_CFLAGS)
+
 ALL_HOST_CFLAGS := \
- $(COMMON_CFLAGS) -Wpointer-arith -Wunused-parameter
+ $(COMMON_USER_FLAGS) $(COMMON_CFLAGS) $(HOST_WARNING_CFLAGS)
 
 # User C++ only
 #
 ALL_CXXFLAGS := \
- $(COMMON_FLAGS) -fno-rtti -fno-exceptions \
- -Wpointer-arith -Wunused-parameter $(SYS_CXXFLAGS)
+ $(COMMON_USER_FLAGS) $(COMMON_FLAGS) \
+ -fno-rtti -fno-exceptions \
+ -Wpointer-arith -Wunused-parameter \
+ $(SYS_CXXFLAGS)
+
+ALL_HOST_CXXFLAGS := \
+ $(COMMON_USER_FLAGS) $(COMMON_CFLAGS) -Wall
 
 # User C and C++
 #
@@ -118,9 +201,11 @@ ALL_LDFLAGS += $(SYS_LDFLAGS)
 
 # Kernel C only
 #
-ALL_KBUILD_CFLAGS := $(COMMON_CFLAGS) -Wno-unused-parameter -Wno-sign-compare \
- $(call cc-option,-Wno-type-limits) \
- $(call cc-option,-Wno-unused-but-set-variable)
+ALL_KBUILD_CFLAGS := $(COMMON_CFLAGS) $(KBUILD_WARNING_CFLAGS) \
+ $(call kernel-cc-option,-Wno-type-limits) \
+ $(call kernel-cc-option,-Wno-pointer-arith) \
+ $(call kernel-cc-option,-Wno-aggregate-return) \
+ $(call kernel-cc-option,-Wno-unused-but-set-variable)
 
 # This variable contains a list of all modules built by kbuild
 ALL_KBUILD_MODULES :=
index 35d1988..25e5ed1 100644 (file)
@@ -1,26 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 # from-one-* recipes make a thing from one source file, so they use $<. Others
 # use $(MODULE_something) instead of $^
@@ -174,8 +190,6 @@ override CC_CHECK   := $(if $(V),,@)$(MAKE_TOP)/tools/cc-check.sh
 override CXX           := $(if $(V),,@)$(CROSS_COMPILE)$(CXX)
 override CHMOD         := $(if $(V),,@)chmod
 override CP                    := $(if $(V),,@)cp
-override DOS2UNIX      := $(if $(V),,@)\
- $(shell if [ -z `which fromdos` ]; then echo dos2unix -f -q; else echo fromdos -f -p; fi)
 override ECHO          := $(if $(V),,@)echo
 override FLEX          := $(if $(V),,@)flex
 override GAWK          := $(if $(V),,@)gawk
index f0a8ef0..fc87c2f 100644 (file)
@@ -1,29 +1,48 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Title         XOrg root makefile
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 ifeq ($(filter xorg,$(EXCLUDED_APIS)),)
- COMPONENTS += xorg pvr_conf pvr_video wsegl_dri2_linux
+ COMPONENTS += xorg pvr_conf pvr_video pvr_video_bin wsegl_dri2_linux
  -include ../common/apis/xorg_opengl.mk
+ifeq ($(SUPPORT_PVR_REMOTE),1)
+ COMPONENTS += pvr_input
+endif
 endif
index 5979012..5d0289f 100644 (file)
@@ -1,30 +1,46 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 $(eval $(call TunableBothConfigC,SUPPORT_DRI_DRM,))
 $(eval $(call TunableBothConfigC,SUPPORT_DRI_DRM_EXT,))
+$(eval $(call TunableKernelConfigC,SUPPORT_DRI_DRM_PLUGIN,))
 
 
 $(eval $(call TunableBothConfigMake,SUPPORT_DRI_DRM,))
@@ -33,6 +49,7 @@ ifeq ($(SUPPORT_DRI_DRM),1)
 ifeq ($(SUPPORT_DRI_DRM_NO_LIBDRM),1)
 endif
 $(eval $(call TunableKernelConfigC,PVR_SECURE_DRM_AUTH_EXPORT,))
+$(eval $(call TunableKernelConfigC,SUPPORT_DRM_MODESET,))
 endif
 
 $(eval $(call TunableKernelConfigC,PVR_DISPLAY_CONTROLLER_DRM_IOCTL,))
@@ -42,4 +59,5 @@ $(eval $(call TunableBothConfigMake,PVR_DRI_DRM_NOT_PCI))
 
 $(eval $(call TunableKernelConfigC,PVR_DRI_DRM_PLATFORM_DEV,))
 
+
 export EXTERNAL_3PDD_TARBALL
index 8c0a172..153159a 100644 (file)
@@ -1,27 +1,43 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
-$(eval $(call TunableBothConfigC,PVR_NO_FULL_CACHE_OPS,))
 $(eval $(call TunableKernelConfigC,PVR_NO_OMAP_TIMER,))
+$(eval $(call TunableKernelConfigC,PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY,))
+$(eval $(call TunableKernelConfigC,PVR_OMAPLFB_DRM_FB,))
index 42c0ed0..b5f84d4 100644 (file)
@@ -1,24 +1,40 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
index f503460..27c77a3 100644 (file)
@@ -1,28 +1,48 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 PVR_SECURE_DRM_AUTH_EXPORT := 1
 
 $(eval $(call TunableKernelConfigC,XPROC_WORKAROUND_NUM_SHAREABLES,4095))
 
+ifeq ($(SUPPORT_PVR_REMOTE),1)
+else
+endif
+
index 6e7552f..a1b4009 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 # FIXME: Will go away when SUPPORT_DRI_DRM is untangled from
 #        the old meaning of SUPPORT_XORG=1.
index 1c87e16..8eb0824 100644 (file)
@@ -1,27 +1,43 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Title         Root build configuration.
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 # Configuration wrapper for new build system. This file deals with
 # configuration of the build. Add to this file anything that deals
@@ -110,10 +126,6 @@ endef
 
 ############################### END MACROS ##################################
 
-DOS2UNIX := $(shell \
- if [ -z `which fromdos` ]; then echo dos2unix -f -q; else echo fromdos -f -p; fi \
-)
-
 # Check we have a new enough version of GNU make.
 #
 need := 3.81
@@ -142,6 +154,14 @@ endif
 endif
 override EURASIAROOT := $(_GUESSED_EURASIAROOT)
 TOP := $(EURASIAROOT)
+
+ifneq ($(words $(TOP)),1)
+$(warning This source tree is located in a path which contains whitespace,)
+$(warning which is not supported.)
+$(warning $(space)The root is: $(TOP))
+$(error Whitespace found in $$(TOP))
+endif
+
 $(call directory-must-exist,$(TOP))
 
 include ../defs.mk
@@ -157,6 +177,7 @@ $(call directory-must-exist,$(TOP)/eurasiacon/build/linux2/$(PVR_BUILD_DIR))
 #
 BUILD  ?= release
 OUT            ?= $(TOP)/eurasiacon/binary2_$(PVR_BUILD_DIR)_$(BUILD)
+override OUT := $(if $(filter /%,$(OUT)),$(OUT),$(TOP)/$(OUT))
 
 CONFIG_MK                      := $(OUT)/config.mk
 CONFIG_H                       := $(OUT)/config.h
@@ -250,7 +271,31 @@ override SUPPORT_HW_RECOVERY := 0
 override SUPPORT_ACTIVE_POWER_MANAGEMENT := 0
 endif
 
+# We're bumping against USSE limits on older cores because the ukernel
+# is too large when building both SGX_DISABLE_VISTEST_SUPPORT=0 and
+# PVRSRV_USSE_EDM_STATUS_DEBUG=1.
+#
+# Automatically disable vistest support if debugging the ukernel to
+# prevent build failures.
+#
+ifneq ($(filter 520 530 531 535 540,$(SGXCORE)),)
+ifneq ($(SGX_DISABLE_VISTEST_SUPPORT),1)
+SGX_DISABLE_VISTEST_SUPPORT ?= not-overridden
+ifeq ($(SGX_DISABLE_VISTEST_SUPPORT),not-overridden)
+$(warning Setting SGX_DISABLE_VISTEST_SUPPORT=1 because PVRSRV_USSE_EDM_STATUS_DEBUG=1)
+SGX_DISABLE_VISTEST_SUPPORT := 1
+endif
+endif
+endif
+
 ifeq ($(SGXCORE),535)
+ifeq ($(PVRSRV_USSE_EDM_STATUS_DEBUG),1)
+SUPPORT_SGX_HWPERF ?= not-overridden
+ifeq ($(SUPPORT_SGX_HWPERF),not-overridden)
+$(warning Setting SUPPORT_SGX_HWPERF=0 because PVRSRV_USSE_EDM_STATUS_DEBUG=1)
+SUPPORT_SGX_HWPERF := 0
+endif
+endif
 PVR2D_ALT_2DHW ?= 0
 endif
 
@@ -303,7 +348,7 @@ $(foreach _o,SYS_CFLAGS SYS_CXXFLAGS SYS_EXE_LDFLAGS SYS_LIB_LDFLAGS SUPPORT_EWS
 # Check for words in EXCLUDED_APIS that aren't understood by the
 # common/apis/*.mk files. This should be kept in sync with all the tests on
 # EXCLUDED_APIS in those files
-_excludable_apis := opencl opengl opengles1 opengles2 openvg ews unittests xorg xorg_unittests
+_excludable_apis := opencl opengl opengles1 opengles2 openvg ews unittests xorg xorg_unittests scripts
 _unrecognised := $(strip $(filter-out $(_excludable_apis),$(EXCLUDED_APIS)))
 ifneq ($(_unrecognised),)
 $(warning *** Unrecognised entries in EXCLUDED_APIS: $(_unrecognised))
@@ -328,18 +373,46 @@ KERNEL_COMPONENTS += dbgdrv
 endif
 endif
 
+ifeq ($(SUPPORT_PVR_REMOTE),1)
+ifneq ($(filter pvr2d,$(COMPONENTS)),)
+COMPONENTS += null_pvr2d_remote
+endif
+COMPONENTS += pvrvncsrv
+endif
+
 # If KERNELDIR is set, write it out to the config.mk, with
 # KERNEL_COMPONENTS and KERNEL_ID
 #
 ifneq ($(strip $(KERNELDIR)),)
 include ../kernel_version.mk
+PVRSRV_MODULE_BASEDIR ?= /lib/modules/$(KERNEL_ID)/extra/
 $(eval $(call KernelConfigMake,KERNELDIR,$(KERNELDIR)))
 # Needed only by install script
 $(eval $(call KernelConfigMake,KERNEL_COMPONENTS,$(KERNEL_COMPONENTS)))
-$(eval $(call TunableKernelConfigMake,KERNEL_CROSS_COMPILE,))
 $(eval $(call TunableKernelConfigMake,EXTRA_PVRSRVKM_COMPONENTS,))
 $(eval $(call TunableKernelConfigMake,EXTRA_KBUILD_SOURCE,))
+
+# If KERNEL_CROSS_COMPILE is set to "undef", this is magically
+# equivalent to being unset. If it is unset, we use CROSS_COMPILE
+# (which might also be unset). If it is set, use it directly.
+ifneq ($(KERNEL_CROSS_COMPILE),undef)
+KERNEL_CROSS_COMPILE ?= $(CROSS_COMPILE)
+$(eval $(call TunableBothConfigMake,KERNEL_CROSS_COMPILE,))
+endif
+
+# Check the KERNELDIR has a kernel built and also check that it is
+# not 64-bit, which we do not support.
+VMLINUX := $(strip $(wildcard $(KERNELDIR)/vmlinux))
+ifneq ($(VMLINUX),)
+VMLINUX_IS_64BIT := $(shell file $(VMLINUX) | grep -q 64-bit || echo false)
+ifneq ($(VMLINUX_IS_64BIT),false)
+$(warning $$(KERNELDIR)/vmlinux is 64-bit, which is not supported. Kbuild may fail.)
+endif
+else
+$(warning $$(KERNELDIR)/vmlinux does not exist. Kbuild may fail.)
 endif
+endif
+
 
 # Ideally configured by platform Makefiles, as necessary
 #
@@ -349,7 +422,6 @@ endif
 $(eval $(call BothConfigC,LINUX,))
 
 $(eval $(call BothConfigC,PVR_BUILD_DIR,"\"$(PVR_BUILD_DIR)\""))
-$(eval $(call BothConfigC,PVR_BUILD_DATE,"\"\""))
 $(eval $(call BothConfigC,PVR_BUILD_TYPE,"\"$(BUILD)\""))
 $(eval $(call BothConfigC,PVRSRV_MODNAME,"\"$(PVRSRV_MODNAME)\""))
 
@@ -364,7 +436,21 @@ $(eval $(call TunableBothConfigC,USE_SGX_CORE_REV_HEAD,))
 $(eval $(call BothConfigC,TRANSFER_QUEUE,))
 $(eval $(call BothConfigC,PVR_SECURE_HANDLES,))
 
-$(eval $(call KernelConfigC,DISPLAY_CONTROLLER,$(DISPLAY_CONTROLLER)))
+ifneq ($(DISPLAY_CONTROLLER),)
+$(eval $(call BothConfigC,DISPLAY_CONTROLLER,$(DISPLAY_CONTROLLER)))
+endif
+
+PVR_LINUX_MEM_AREA_POOL_MAX_PAGES ?= 0
+ifneq ($(PVR_LINUX_MEM_AREA_POOL_MAX_PAGES),0)
+PVR_LINUX_MEM_AREA_USE_VMAP ?= 1
+include ../kernel_version.mk
+ifeq ($(call kernel-version-at-least,3,0),true)
+PVR_LINUX_MEM_AREA_POOL_ALLOW_SHRINK ?= 1
+endif
+endif
+$(eval $(call KernelConfigC,PVR_LINUX_MEM_AREA_POOL_MAX_PAGES,$(PVR_LINUX_MEM_AREA_POOL_MAX_PAGES)))
+$(eval $(call TunableKernelConfigC,PVR_LINUX_MEM_AREA_USE_VMAP,))
+$(eval $(call TunableKernelConfigC,PVR_LINUX_MEM_AREA_POOL_ALLOW_SHRINK,))
 
 
 $(eval $(call BothConfigMake,PVR_SYSTEM,$(PVR_SYSTEM)))
@@ -403,7 +489,6 @@ $(eval $(call TunableBothConfigC,SUPPORT_MEMINFO_IDS,))
 $(eval $(call TunableBothConfigC,SUPPORT_SGX_NEW_STATUS_VALS,1))
 $(eval $(call TunableBothConfigC,SUPPORT_PDUMP_MULTI_PROCESS,))
 $(eval $(call TunableBothConfigC,SUPPORT_DBGDRV_EVENT_OBJECTS,1))
-$(eval $(call TunableBothConfigC,PVR_DBG_BREAK_ASSERT_FAIL,))
 $(eval $(call TunableBothConfigC,SGX_FEATURE_SYSTEM_CACHE,))
 $(eval $(call TunableBothConfigC,SGX_BYPASS_SYSTEM_CACHE,))
 $(eval $(call TunableBothConfigC,SGX_BYPASS_DCU,))
@@ -415,19 +500,26 @@ $(eval $(call TunableBothConfigC,PDUMP,))
 $(eval $(call TunableBothConfigC,NO_HARDWARE,))
 $(eval $(call TunableBothConfigC,PDUMP_DEBUG_OUTFILES,))
 $(eval $(call TunableBothConfigC,PVRSRV_USSE_EDM_STATUS_DEBUG,))
+$(eval $(call TunableBothConfigC,SGX_DISABLE_VISTEST_SUPPORT,))
 $(eval $(call TunableBothConfigC,PVRSRV_RESET_ON_HWTIMEOUT,))
 $(eval $(call TunableBothConfigC,SYS_USING_INTERRUPTS,1))
 $(eval $(call TunableBothConfigC,SUPPORT_EXTERNAL_SYSTEM_CACHE,))
+$(eval $(call TunableBothConfigC,PVRSRV_NEW_PVR_DPF,))
 $(eval $(call TunableBothConfigC,PVRSRV_NEED_PVR_DPF,))
 $(eval $(call TunableBothConfigC,PVRSRV_NEED_PVR_ASSERT,))
 $(eval $(call TunableBothConfigC,PVRSRV_NEED_PVR_TRACE,))
 $(eval $(call TunableBothConfigC,SUPPORT_SECURE_33657_FIX,))
+$(eval $(call TunableBothConfigC,SUPPORT_ION,))
+$(eval $(call TunableBothConfigC,SUPPORT_HWRECOVERY_TRACE_LIMIT,))
+$(eval $(call TunableBothConfigC,SUPPORT_PVRSRV_GET_DC_SYSTEM_BUFFER,1))
+$(eval $(call TunableBothConfigC,SUPPORT_NV12_FROM_2_HWADDRS,))
 
 $(eval $(call TunableKernelConfigC,SUPPORT_LINUX_X86_WRITECOMBINE,1))
 $(eval $(call TunableKernelConfigC,SUPPORT_LINUX_X86_PAT,1))
 $(eval $(call TunableKernelConfigC,SGX_DYNAMIC_TIMING_INFO,))
 $(eval $(call TunableKernelConfigC,SYS_SGX_ACTIVE_POWER_LATENCY_MS,))
 $(eval $(call TunableKernelConfigC,SYS_CUSTOM_POWERLOCK_WRAP,))
+$(eval $(call TunableKernelConfigC,SYS_SUPPORTS_SGX_IDLE_CALLBACK,))
 $(eval $(call TunableKernelConfigC,PVR_LINUX_USING_WORKQUEUES,))
 $(eval $(call TunableKernelConfigC,PVR_LINUX_MISR_USING_WORKQUEUE,))
 $(eval $(call TunableKernelConfigC,PVR_LINUX_MISR_USING_PRIVATE_WORKQUEUE,))
@@ -435,26 +527,33 @@ $(eval $(call TunableKernelConfigC,PVR_LINUX_TIMERS_USING_WORKQUEUES,))
 $(eval $(call TunableKernelConfigC,PVR_LINUX_TIMERS_USING_SHARED_WORKQUEUE,))
 $(eval $(call TunableKernelConfigC,LDM_PLATFORM,))
 $(eval $(call TunableKernelConfigC,PVR_LDM_PLATFORM_PRE_REGISTERED,))
+$(eval $(call TunableKernelConfigC,PVR_LDM_PLATFORM_PRE_REGISTERED_DEV,))
+$(eval $(call TunableKernelConfigC,PVR_LDM_DRIVER_REGISTRATION_NAME,"\"$(PVRSRV_MODNAME)\""))
 $(eval $(call TunableKernelConfigC,LDM_PCI,))
 $(eval $(call TunableKernelConfigC,PVRSRV_DUMP_MK_TRACE,))
 $(eval $(call TunableKernelConfigC,PVRSRV_DUMP_KERNEL_CCB,))
+$(eval $(call TunableKernelConfigC,PVRSRV_REFCOUNT_DEBUG,))
+$(eval $(call TunableKernelConfigC,PVRSRV_MMU_MAKE_READWRITE_ON_DEMAND,))
 $(eval $(call TunableKernelConfigC,HYBRID_SHARED_PB_SIZE,))
+$(eval $(call TunableKernelConfigC,SUPPORT_LARGE_GENERAL_HEAP,))
+$(eval $(call TunableKernelConfigC,TTRACE,))
 
 
-$(eval $(call TunableBothConfigMake,LDM_PLATFORM,))
-$(eval $(call TunableBothConfigMake,LDM_PCI,))
+$(eval $(call TunableBothConfigMake,SUPPORT_ION,))
 
 
 $(eval $(call TunableBothConfigMake,OPTIM,))
 
 
+$(eval $(call TunableKernelConfigMake,TTRACE,))
+
 endif # INTERNAL_CLOBBER_ONLY
 
 export INTERNAL_CLOBBER_ONLY
 export TOP
 export OUT
 
-MAKE_ETC := -Rr --no-print-directory -C $(TOP) TOP=$(TOP) \
+MAKE_ETC := -Rr --no-print-directory -C $(TOP) TOP=$(TOP) OUT=$(OUT) \
                -f eurasiacon/build/linux2/toplevel.mk
 
 # This must match the default value of MAKECMDGOALS below, and the default
@@ -472,8 +571,8 @@ endif
 autogen:
 ifeq ($(INTERNAL_CLOBBER_ONLY),)
        @$(MAKE) -s --no-print-directory -C $(EURASIAROOT) \
-               DOS2UNIX="$(DOS2UNIX)" \
-               -f eurasiacon/build/linux2/prepare_tree.mk
+               -f eurasiacon/build/linux2/prepare_tree.mk \
+               LDM_PCI=$(LDM_PCI) LDM_PLATFORM=$(LDM_PLATFORM)
 else
        @:
 endif
index d4cfe29..621e03e 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 define must-be-defined
 $(if $(filter undefined,$(origin $(1))),$(error In makefile $(THIS_MAKEFILE): $$($(1)) must be defined),)
@@ -81,7 +96,6 @@ endef
 define cc-check
 $(shell \
        CC_CHECK=$(patsubst @%,%,$(CC_CHECK)) && \
-       $(patsubst @%,%,$(DOS2UNIX)) $$CC_CHECK && \
        $(patsubst @%,%,$(CHMOD)) +x $$CC_CHECK && \
        $$CC_CHECK --cc "$(1)" --out "$(2)" $(3))
 endef
@@ -101,3 +115,26 @@ endef
 define host-cc-option
 $(call cc-check,$(patsubst @%,%,$(HOST_CC)),$(OUT),$(1))
 endef
+
+define kernel-cc-option
+$(call cc-check,$(KERNEL_CROSS_COMPILE)gcc,$(OUT),$(1))
+endef
+
+# Turn a particular warning on, or explicitly turn it off, depending on
+# the value of W. The "-W" or "-Wno-" part of the warning need not be
+# specified.
+define cc-optional-warning
+$(call cc-option,-W$(if $(W),,no-)$(patsubst -W%,%,$(patsubst -Wno-%,%,$(1))))
+endef
+
+define host-cc-optional-warning
+$(call host-cc-option,-W$(if $(W),,no-)$(patsubst -W%,%,$(patsubst -Wno-%,%,$(1))))
+endef
+
+define kernel-cc-optional-warning
+$(call kernel-cc-option,-W$(if $(W),,no-)$(patsubst -W%,%,$(patsubst -Wno-%,%,$(1))))
+endef
+
+define module-info-line
+$(if $(filter modules,$(D)),$(info $(1)),)
+endef
index 4804e94..09ce3dc 100644 (file)
@@ -1,27 +1,43 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Title         Root kernel makefile
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 # This top-level kbuild makefile builds all the Linux kernel modules in the
 # DDK. To run kbuild, this makefile is copied to $(TARGET_OUT)/kbuild/Makefile
@@ -55,7 +71,6 @@ ccflags-y += -D__linux__ -include $(OUT)/config_kernel.h \
  -I$(TOP)/services4/include \
  -I$(TOP)/services4/system/$(PVR_SYSTEM) \
  -I$(TOP)/services4/system/include \
- -I$(TOP)/services4/srvkm/hwdefs \
  -I$(TOP)/services4/srvkm/bridged \
  -I$(TOP)/services4/srvkm/bridged/sgx \
  -I$(TOP)/services4/srvkm/common \
@@ -63,6 +78,12 @@ ccflags-y += -D__linux__ -include $(OUT)/config_kernel.h \
  -I$(TOP)/services4/srvkm/env/linux \
  -I$(TOP)/services4/srvkm/include
 
+ifeq ($(PVR_LOCAL_HWDEFS),)
+ccflags-y += -I$(TOP)/services4/srvkm/hwdefs
+else
+ccflags-y += -I$(TOP)/hwdefs
+endif
+
 include $(INTERNAL_KBUILD_MAKEFILES)
 
 $(if $(pvrsrvkm-y),,$(error pvrsrvkm-y was empty, which could mean that srvkm is missing from $$(KERNEL_COMPONENTS)))
index caa58ed..d3aa147 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 ifneq ($(EXTERNAL_3PDD_TARBALL),)
 TAR_OPT_STRIP_COMPONENTS ?= --strip-components
index 2d973af..94e2100 100644 (file)
@@ -1,35 +1,46 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
-
-include $(CONFIG_KERNEL_MK)
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 $(if $(strip $(KERNELDIR)),,$(error KERNELDIR must be set))
 $(call directory-must-exist,$(KERNELDIR))
 
-KERNEL_CROSS_COMPILE ?= $(CROSS_COMPILE)
-
 $(TARGET_OUT)/kbuild/Makefile: $(MAKE_TOP)/kbuild/Makefile.template
        @[ ! -e $(dir $@) ] && mkdir -p $(dir $@) || true
        $(CP) -f $< $@
@@ -51,11 +62,6 @@ kbuild: $(TARGET_OUT)/kbuild/Makefile
                EXTRA_CFLAGS="$(ALL_KBUILD_CFLAGS)" \
                V=$(V) W=$(W) \
                TOP=$(TOP)
-ifeq ($(DEBUGLINK),1)
-       @for kernel_module in $(addprefix $(TARGET_OUT)/kbuild/,$(INTERNAL_KBUILD_OBJECTS:.o=.ko)); do \
-               $(patsubst @%,%,$(STRIP)) --strip-unneeded $$kernel_module; \
-       done
-endif
        @for kernel_module in $(addprefix $(TARGET_OUT)/kbuild/,$(INTERNAL_KBUILD_OBJECTS:.o=.ko)); do \
                cp $$kernel_module $(TARGET_OUT); \
        done
index f5db1a8..a0a1289 100644 (file)
@@ -1,26 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 # Rules for making kernel modules with kbuild. This makefile doesn't define
 # any rules that build the modules, it only copies the kbuild Makefile into
index 8ed6aaa..35ecceb 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 $(if $(KERNELDIR),,$(error KERNELDIR must be set to obtain a version))
 
@@ -34,28 +49,52 @@ override KERNEL_SUBLEVEL := \
 override KERNEL_EXTRAVERSION := \
  $(shell grep "^EXTRAVERSION = " $(KERNELDIR)/Makefile | cut -f3 -d' ')
 
+# Break the kernel version up into a space separated list
+kernel_version_as_list := $(KERNEL_VERSION) \
+                               $(KERNEL_PATCHLEVEL) \
+                               $(KERNEL_SUBLEVEL) \
+                               $(patsubst .%,%,$(KERNEL_EXTRAVERSION))
+
 # The base ID doesn't have to be accurate; we only use it for
 # feature checks which will not care about extraversion bits
 #
 override KERNEL_BASE_ID := \
  $(KERNEL_VERSION).$(KERNEL_PATCHLEVEL).$(KERNEL_SUBLEVEL)
 
-# UTS_RELEASE is more accurate, if we can find it
-# If we can't, fall back to manufacturing the version
-#
+# Try to get the kernel ID from the kernel.release file.
+# 
 KERNEL_ID ?= \
- $(shell grep -h '\#define UTS_RELEASE' \
-       $(KERNELDIR)/include/linux/* | cut -f3 -d' ' | sed s/\"//g)
+ $(shell cat $(KERNELDIR)/include/config/kernel.release 2>/dev/null)
 
+# If the kernel ID isn't set yet, try to set it from the UTS_RELEASE
+# macro.
+#
 ifeq ($(strip $(KERNEL_ID)),)
-# kernel.release, it it exists, contains what UTS_RELEASE would have
-# been set to.
-# 
 KERNEL_ID := \
- $(shell cat $(KERNELDIR)/include/config/kernel.release 2>/dev/null)
+ $(shell grep -h '\#define UTS_RELEASE' \
+       $(KERNELDIR)/include/linux/* | cut -f3 -d' ' | sed s/\"//g)
 endif
 
 ifeq ($(strip $(KERNEL_ID)),)
 KERNEL_ID := \
  $(KERNEL_VERSION).$(KERNEL_PATCHLEVEL).$(KERNEL_SUBLEVEL)$(KERNEL_EXTRAVERSION)
 endif
+
+# Return 1 if the kernel version is at least the value passed to the
+# function, else return nothing.
+# Examples
+#      $(call kernel-version-at-least,2,6,35)
+#      $(call kernel-version-at-least,2,6,35,7)
+#
+define kernel-version-at-least
+$(shell set -- $(kernel_version_as_list) 0 0 0 0; \
+       Y=true; \
+       for D in $1 $2 $3 $4; \
+       do \
+               [ $$1 ] || break; \
+               [ $$1 -eq $$D ] && { shift; continue; };\
+               [ $$1 -lt $$D ] && Y=; \
+               break; \
+       done; \
+       echo $$Y)
+endef
index 2569099..869026f 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 MODULE_TARGETS :=
 MODULE_CFLAGS := $(ALL_CFLAGS) $($(THIS_MODULE)_cflags)
index 9bc52a3..1576590 100644 (file)
@@ -1,27 +1,43 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Title         Module processing
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 # Bits for processing $(modules) after reading in each Linux.mk
 
index 0f3a35b..6d0e81a 100644 (file)
@@ -1,27 +1,43 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Title         Root makefile for OMAP4430 Linux.  Builds everything else.
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 PVR_SYSTEM             := omap4
 
@@ -29,10 +45,6 @@ KERNEL_COMPONENTS := srvkm bufferclass_example
 
 include ../kernel_version.mk
 
-OMAP_KERNEL_AT_LEAST_2_6_35 := $(shell test $(KERNEL_VERSION) -ge 2 -a \
-                       $(KERNEL_PATCHLEVEL) -ge 6 -a \
-                       $(KERNEL_SUBLEVEL) -ge 35 && echo 1 || echo 0)
-
 # Only enable active power management if passive power management is
 # enabled, as indicated by LDM_PLATFORM being set to 1.  On OMAP,
 # the system can suspend in the case where active power management is
@@ -66,8 +78,6 @@ ifeq ($(SUPPORT_OMAP4430_NEON),1)
 SYS_CFLAGS += -ftree-vectorize -mfpu=neon -mfloat-abi=softfp
 endif
 
-PVR_NO_FULL_CACHE_OPS := 1
-
 LIBGCC := $(shell $(CROSS_COMPILE)gcc -print-libgcc-file-name)
 
 SGXCORE := 540
@@ -82,9 +92,31 @@ else
 OPK_DEFAULT := libpvrPVR2D_FLIPWSEGL.so
 endif
 
-ifeq ($(OMAP_KERNEL_AT_LEAST_2_6_35),1)
+ifeq ($(call kernel-version-at-least,2,6,35),true)
+# Work around flipping problems seen with the Taal LCDs on Blaze.
+# The work around is safe to use with other types of screen on Blaze
+# (e.g. HDMI) and on other platforms (e.g. Panda board).
+PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY := 1
 ifeq ($(LDM_PLATFORM),1)
 PVR_LDM_PLATFORM_PRE_REGISTERED := 1
+ifeq ($(call kernel-version-at-least,2,6,35,7),true)
+# Not all variants of the OMAP4 kernel have a DRM based framebuffer.
+# Note that a non-X.Org version of the driver does not have to be built
+# with DRM support if the kernel has a DRM based framebuffer.
+PVR_OMAPLFB_DRM_FB ?= 1
+ifeq ($(PVR_OMAPLFB_DRM_FB),1)
+PVR_LDM_PLATFORM_PRE_REGISTERED_DEV := "\"pvrsrvkm_pvr\""
+# There is already a "pvrsrvkm" driver (part of the DRM framebuffer code),
+# so use the pre-registered device name instead.
+PVR_LDM_DRIVER_REGISTRATION_NAME := "\"pvrsrvkm_pvr"\"
+# The DRM library will not load the Services module on behalf of the X Server,
+# as a DRM module has already been loaded (the DRM based framebuffer), so
+# load the Services module before starting the X Server.
+XORG_EXPLICIT_PVR_SERVICES_LOAD := 1
+else
+PVR_LDM_PLATFORM_PRE_REGISTERED_DEV := "\"pvrsrvkm\""
+endif
+endif
 endif
 endif
 
@@ -93,14 +125,29 @@ ifeq ($(want_xorg),1)
 
 SUPPORT_DRI_DRM := 1
 
-ifeq ($(OMAP_KERNEL_AT_LEAST_2_6_35),1)
+ifeq ($(call kernel-version-at-least,2,6,35),true)
 PVR_DRI_DRM_PLATFORM_DEV := 1
 PVR_DRI_DRM_STATIC_BUS_ID := 1
+ifeq ($(call kernel-version-at-least,2,6,35,7),true)
+ifeq ($(PVR_OMAPLFB_DRM_FB),1)
+SUPPORT_DRI_DRM_PLUGIN := 1
+endif
+ifeq ($(call kernel-version-at-least,2,6,36),true)
+PVR_DRI_DRM_DEV_BUS_ID := "\"platform:pvrsrvkm"\"
+else
+PVR_DRI_DRM_DEV_BUS_ID := "\"platform:pvrsrvkm:00"\"
+endif
+# A client DRI authorisation failure, whilst switched away from the X Server
+# VT, prevents all other attempts at DRI authorisation, even after
+# switching back to the X server VT, so don't perform a DRM drop master
+# call.
+PVR_XORG_DONT_DROP_MASTER_IN_LEAVE_VT := 1
+endif
 else
 PVR_DRI_DRM_NOT_PCI := 1
 endif
 
-XORG_TOOLCHAIN := tarballs-omap4-ubuntu-10.10-cross
+XORG_TOOLCHAIN ?= tarballs-omap4-ubuntu-10.10-cross
 XORG_PVR_CONF := omap4
 XORG_PVR_VIDEO := omap4
 
index e1e18da..05e4fe3 100644 (file)
@@ -1,29 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
-
--include $(OUT)/config.mk.new
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 .PHONY: prepare_tree
 
index 2410804..c312001 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 # Find out the path of the Linux.mk makefile currently being processed, and
 # set paths used by the build rules
index 7d6d75c..6cef8fa 100644 (file)
@@ -1,34 +1,62 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+#!/bin/sh
+########################################################################### ###
+#@Title         Test the nature of the C compiler.
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
+# 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
 # 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
+
+LANG=C
+export LANG
 
 usage() {
        echo "usage: $0 [--64] --cc CC --out OUT [cflag]"
        exit 1
 }
 
+# NOTE: The program passed to the compiler is deliberately incorrect
+# (`return;' should be `return 0;') but we do this to emit a warning.
+#
+# Emitting a warning is necessary to get GCC to print out additional
+# warnings about any unsupported -Wno options, so we can handle these
+# as unsupported by the build.
+#
 do_cc() {
-       echo "int main(void){return 0;}" | $CC $1 -xc -c - -o $ccof 2>/dev/null
+       echo "int main(void){return;}" | $CC -W -Wall $3 -xc -c - -o $1 >$2 2>&1
 }
 
 while [ 1 ]; do
@@ -51,16 +79,21 @@ done
 [ "x$CC" = "x" ] && usage
 [ "x$OUT" = "x" ] && usage
 ccof=$OUT/cc-sanity-check
+log=${ccof}.log
 
 if [ "x$BIT_CHECK" = "x1" ]; then
-       do_cc ""
-       file $ccof | grep -q 64-bit
+       do_cc $ccof $log ""
+       file $ccof | grep 64-bit >/dev/null 2>&1
        [ "$?" = "0" ] && echo true || echo false
 else
        [ "x$1" = "x" ] && usage
-       do_cc $1
-       [ "$?" = "0" ] && echo $1
+       do_cc $ccof $log $1
+       if [ "$?" = "0" ]; then
+               # compile passed, but was the warning unrecognized?
+               grep -q "^cc1: warning: unrecognized command line option \"$1\"" $log
+               [ "$?" = "1" ] && echo $1
+       fi
 fi
 
-rm -f $ccof
+rm -f $ccof $log
 exit 0
index 79f906c..26b1198 100644 (file)
@@ -1,33 +1,47 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
-
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 # Define the default goal. This masks a previous definition of the default
 # goal in Makefile.config, which must match this one
 .PHONY: build
-build: components kbuild scripts
+build: components kbuild
 
 ifeq ($(OUT),)
 $(error "Must specify output directory with OUT=")
@@ -53,6 +67,14 @@ CONFIG_KERNEL_H              := $(RELATIVE_OUT)/config_kernel.h
 MAKE_TOP                       := eurasiacon/build/linux2
 THIS_MAKEFILE          := (top-level makefiles)
 
+# Convert commas to spaces in $(D). This is so you can say "make
+# D=config-changes,freeze-config" and have $(filter config-changes,$(D))
+# still work.
+comma := ,
+empty :=
+space := $(empty) $(empty)
+override D := $(subst $(comma),$(space),$(D))
+
 include $(MAKE_TOP)/defs.mk
 
 ifneq ($(INTERNAL_CLOBBER_ONLY),true)
@@ -68,15 +90,33 @@ $(HOST_OUT) $(TARGET_OUT):
 # If these generated files differ from any pre-existing ones,
 # replace them, causing affected parts of the driver to rebuild.
 #
-$(shell \
+_want_config_diff := $(filter config-changes,$(D))
+_freeze_config := $(strip $(filter freeze-config,$(D)))
+_updated_config_files := $(shell \
+    $(if $(_want_config_diff),rm -f $(OUT)/config.diff;,) \
        for file in $(CONFIG_MK) $(CONFIG_H) \
                                $(CONFIG_KERNEL_MK) $(CONFIG_KERNEL_H); do \
-               diff -q $$file $$file.new >/dev/null 2>/dev/null \
+               diff -U 0 $$file $$file.new \
+                       >>$(if $(_want_config_diff),$(OUT)/config.diff,/dev/null) 2>/dev/null \
                && rm -f $$file.new \
-               || mv -f $$file.new $$file >/dev/null 2>/dev/null; \
+               || echo $$file; \
        done)
+
+ifneq ($(_want_config_diff),)
+# We send the diff to stderr so it isn't captured by $(shell)
+$(shell [ -s $(OUT)/config.diff ] && echo >&2 "Configuration changed in $(RELATIVE_OUT):" && cat >&2 $(OUT)/config.diff)
+endif
+
+ifneq ($(_freeze_config),)
+$(if $(_updated_config_files),$(error Configuration change in $(RELATIVE_OUT) prevented by D=freeze-config),)
 endif
 
+# Update the config, if changed
+$(foreach _f,$(_updated_config_files), \
+       $(shell mv -f $(_f).new $(_f) >/dev/null 2>/dev/null))
+
+endif # INTERNAL_CLOBBER_ONLY
+
 MAKEFLAGS := -Rr --no-print-directory
 
 ifneq ($(INTERNAL_CLOBBER_ONLY),true)
@@ -84,7 +124,7 @@ ifneq ($(INTERNAL_CLOBBER_ONLY),true)
 # This is so you can say "find $(TOP) -name Linux.mk > /tmp/something; export
 # ALL_MAKEFILES=/tmp/something; make" and avoid having to run find. This is
 # handy if your source tree is mounted over NFS or something
-override ALL_MAKEFILES := $(call relative-to-top,$(if $(strip $(ALL_MAKEFILES)),$(shell cat $(ALL_MAKEFILES)),$(shell find $(TOP) -type f -name Linux.mk)))
+override ALL_MAKEFILES := $(call relative-to-top,$(if $(strip $(ALL_MAKEFILES)),$(shell cat $(ALL_MAKEFILES)),$(shell find $(TOP) -type f -name Linux.mk -print -o -type d -name '.*' -prune)))
 ifeq ($(strip $(ALL_MAKEFILES)),)
 $(info ** Unable to find any Linux.mk files under $$(TOP). This could mean that)
 $(info ** there are no makefiles, or that ALL_MAKEFILES is set in the environment)
@@ -96,12 +136,15 @@ else # clobber-only
 ALL_MAKEFILES :=
 endif
 
+unexport ALL_MAKEFILES
+
 REMAINING_MAKEFILES := $(ALL_MAKEFILES)
 ALL_MODULES :=
 INTERNAL_INCLUDED_ALL_MAKEFILES :=
 
 ifneq ($(INTERNAL_CLOBBER_ONLY),true)
--include $(CONFIG_MK)
+# Please do not change the format of the following lines
+-include $(CONFIG_KERNEL_MK)
 # These files may not exist in GPL km source packages
 -include $(MAKE_TOP)/xorgconf.mk
 -include $(MAKE_TOP)/llvm.mk
@@ -127,8 +170,8 @@ endif
 # each module: for each module in $(ALL_MODULES), set per-makefile variables
 $(foreach _m,$(ALL_MODULES),$(eval $(call process-module,$(_m))))
 
-.PHONY: kbuild scripts install
-kbuild scripts install:
+.PHONY: kbuild install
+kbuild install:
 
 ifneq ($(INTERNAL_CLOBBER_ONLY),true)
 -include $(MAKE_TOP)/scripts.mk
@@ -157,34 +200,11 @@ endif
 
 # You can say 'make all_modules' to attempt to make everything, or 'make
 # components' to only make the things which are listed (in the per-build
-# makefiles) as components of the build. 'make scripts' generates the
-# install.sh and rc.pvr scripts.
-.PHONY: all_modules components scripts
+# makefiles) as components of the build.
+.PHONY: all_modules components
 all_modules: $(ALL_MODULES)
 components: $(COMPONENTS)
 
-# 'make opk' builds the OEM Porting Kit. The build should set OPK_COMPONENTS
-# in components.mk if it should be possible to build the OPK for it
-.PHONY: opk
-ifneq ($(strip $(OPK_COMPONENTS)),)
-opk: $(OPK_COMPONENTS)
-
-opk_clobber: MODULE_DIRS_TO_REMOVE := $(addprefix $(OUT)/target/intermediates/,$(OPK_COMPONENTS))
-opk_clobber: OPK_OUTFILES := $(addprefix $(RELATIVE_OUT)/target/,$(foreach _c,$(OPK_COMPONENTS),$(if $($(_c)_target),$($(_c)_target),$(error Module $(_c) must be a shared library which sets $$($(_c)_target) for OPK clobbering))))
-opk_clobber:
-       $(clean-dirs)
-       $(if $(V),,@echo "  RM      " $(call relative-to-top,$(OPK_OUTFILES)))
-       $(RM) -f $(OPK_OUTFILES)
-else
-# OPK_COMPONENTS is empty or unset
-opk:
-       @echo
-       @echo "** This build ($(PVR_BUILD_DIR)) is unable to build the OPK, because"
-       @echo "** OPK_COMPONENTS is empty or unset. Cannot continue."
-       @echo
-       @false
-endif
-
 # Cleaning
 .PHONY: clean clobber
 clean: MODULE_DIRS_TO_REMOVE := $(OUT)/host/intermediates $(OUT)/target/intermediates $(OUT)/target/kbuild
index b7614ac..753f8f2 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Debug driver
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Debug Driver Interface
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _DBGDRVIF_
 #define _DBGDRVIF_
@@ -43,6 +59,9 @@
 
 #endif
 
+/*****************************************************************************
+ Stream mode stuff.
+*****************************************************************************/
 #define DEBUG_CAPMODE_FRAMED                   0x00000001UL
 #define DEBUG_CAPMODE_CONTINUOUS               0x00000002UL
 #define DEBUG_CAPMODE_HOTKEY                   0x00000004UL
 
 #define DEBUG_FLAGS_TEXTSTREAM                 0x80000000UL
 
+/*****************************************************************************
+ Debug level control. Only bothered with the first 12 levels, I suspect you
+ get the idea...
+*****************************************************************************/
 #define DEBUG_LEVEL_0                                  0x00000001UL
 #define DEBUG_LEVEL_1                                  0x00000003UL
 #define DEBUG_LEVEL_2                                  0x00000007UL
 #define DEBUG_LEVEL_SEL10                              0x00000400UL
 #define DEBUG_LEVEL_SEL11                              0x00000800UL
 
+/*****************************************************************************
+ IOCTL values.
+*****************************************************************************/
 #define DEBUG_SERVICE_IOCTL_BASE               0x800UL
 #define DEBUG_SERVICE_CREATESTREAM             CTL_CODE(FILE_DEVICE_UNKNOWN, DEBUG_SERVICE_IOCTL_BASE + 0x01, METHOD_BUFFERED, FILE_ANY_ACCESS)
 #define DEBUG_SERVICE_DESTROYSTREAM            CTL_CODE(FILE_DEVICE_UNKNOWN, DEBUG_SERVICE_IOCTL_BASE + 0x02, METHOD_BUFFERED, FILE_ANY_ACCESS)
@@ -121,6 +147,9 @@ typedef enum _DBG_EVENT_
 } DBG_EVENT;
 
 
+/*****************************************************************************
+ In/Out Structures
+*****************************************************************************/
 typedef struct _DBG_IN_CREATESTREAM_
 {
        union
@@ -247,23 +276,33 @@ typedef struct _DBG_IN_WRITE_LF_
        IMG_UINT32 ui32BufferSize;
 } DBG_IN_WRITE_LF, *PDBG_IN_WRITE_LF;
 
+/*
+       Flags for above struct
+*/
 #define WRITELF_FLAGS_RESETBUF         0x00000001UL
 
+/*
+       Common control structure (don't duplicate control in main stream
+       and init phase stream).
+*/
 typedef struct _DBG_STREAM_CONTROL_
 {
-       IMG_BOOL   bInitPhaseComplete;  
-       IMG_UINT32 ui32Flags;                   
+       IMG_BOOL   bInitPhaseComplete;          /*!< init phase has finished */
+       IMG_UINT32 ui32Flags;                   /*!< flags (see DEBUG_FLAGS above) */
 
-       IMG_UINT32 ui32CapMode;                 
-       IMG_UINT32 ui32OutMode;                 
+       IMG_UINT32 ui32CapMode;                 /*!< capturing mode framed/hot key */
+       IMG_UINT32 ui32OutMode;                 /*!< output mode, e.g. files */
        IMG_UINT32 ui32DebugLevel;
        IMG_UINT32 ui32DefaultMode;
-       IMG_UINT32 ui32Start;                   
-       IMG_UINT32 ui32End;                             
-       IMG_UINT32 ui32Current;                 
-       IMG_UINT32 ui32SampleRate;              
+       IMG_UINT32 ui32Start;                   /*!< first capture frame */
+       IMG_UINT32 ui32End;                             /*!< last frame */
+       IMG_UINT32 ui32Current;                 /*!< current frame */
+       IMG_UINT32 ui32SampleRate;              /*!< capture frequency */
        IMG_UINT32 ui32Reserved;
 } DBG_STREAM_CONTROL, *PDBG_STREAM_CONTROL;
+/*
+       Per-buffer control structure.
+*/
 typedef struct _DBG_STREAM_
 {
        struct _DBG_STREAM_ *psNext;
@@ -275,20 +314,24 @@ typedef struct _DBG_STREAM_
        IMG_UINT32 ui32RPtr;
        IMG_UINT32 ui32WPtr;
        IMG_UINT32 ui32DataWritten;
-       IMG_UINT32 ui32Marker;                  
-       IMG_UINT32 ui32InitPhaseWOff;   
-       
-       
-       
-       
-       IMG_CHAR szName[30];            
+       IMG_UINT32 ui32Marker;                  /*!< marker for file splitting */
+       IMG_UINT32 ui32InitPhaseWOff;   /*!< snapshot offset for init phase end for follow-on pdump */
+       IMG_CHAR szName[30];            /* Give this a size, some compilers don't like [] */
 } DBG_STREAM,*PDBG_STREAM;
 
+/*
+ * Allows dbgdrv to notify services when events happen, e.g. pdump.exe starts.
+ * (better than resetting psDevInfo->psKernelCCBInfo->ui32CCBDumpWOff = 0
+ * in SGXGetClientInfoKM.)
+ */
 typedef struct _DBGKM_CONNECT_NOTIFIER_
 {
        IMG_VOID (IMG_CALLCONV *pfnConnectNotifier)             (IMG_VOID);
 } DBGKM_CONNECT_NOTIFIER, *PDBGKM_CONNECT_NOTIFIER;
 
+/*****************************************************************************
+ Kernel mode service table
+*****************************************************************************/
 typedef struct _DBGKM_SERVICE_TABLE_
 {
        IMG_UINT32 ui32Size;
@@ -324,5 +367,15 @@ typedef struct _DBGKM_SERVICE_TABLE_
        IMG_UINT32      (IMG_CALLCONV *pfnWritePersist)                 (PDBG_STREAM psStream,IMG_UINT8 *pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level);
 } DBGKM_SERVICE_TABLE, *PDBGKM_SERVICE_TABLE;
 
+#if defined(__linux__)
+/*****************************************************************************
+ Function to export service table from debug driver to the PDUMP component.
+*****************************************************************************/
+IMG_VOID DBGDrvGetServiceTable(DBGKM_SERVICE_TABLE **fn_table);
+#endif
+
 
 #endif
+/*****************************************************************************
+ End of file (DBGDRVIF.H)
+*****************************************************************************/
index 79a730f..375ed99 100644 (file)
@@ -1,29 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Common header containing type definitions for portability
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Contains variable and structure definitions. Any platform
+                specific types should be defined in this file.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #if !defined (__IMG_DEFS_H__)
 #define __IMG_DEFS_H__
 
@@ -57,24 +73,33 @@ typedef             enum    img_tag_TriStateSwitch
 #endif
 
 
+/* Use this in any file, or use attributes under GCC - see below */
 #ifndef PVR_UNREFERENCED_PARAMETER
 #define        PVR_UNREFERENCED_PARAMETER(param) (param) = (param)
 #endif
 
+/* The best way to supress unused parameter warnings using GCC is to use a
+ * variable attribute.  Place the unref__ between the type and name of an
+ * unused parameter in a function parameter list, eg `int unref__ var'. This
+ * should only be used in GCC build environments, for example, in files that
+ * compile only on Linux. Other files should use UNREFERENCED_PARAMETER */
 #ifdef __GNUC__
 #define unref__ __attribute__ ((unused))
 #else
 #define unref__
 #endif
 
+/*
+       Wide character definitions
+*/
 #ifndef _TCHAR_DEFINED
 #if defined(UNICODE)
 typedef unsigned short         TCHAR, *PTCHAR, *PTSTR;
-#else  
+#else  /* #if defined(UNICODE) */
 typedef char                           TCHAR, *PTCHAR, *PTSTR;
-#endif 
+#endif /* #if defined(UNICODE) */
 #define _TCHAR_DEFINED
-#endif 
+#endif /* #ifndef _TCHAR_DEFINED */
 
 
                        #if defined(__linux__) || defined(__QNXNTO__) || defined(__METAG)
@@ -89,6 +114,7 @@ typedef char                         TCHAR, *PTCHAR, *PTSTR;
                                        #error("define an OS")
                        #endif
 
+// Use default definition if not overridden
 #ifndef IMG_ABORT
        #define IMG_ABORT()     abort()
 #endif
@@ -109,6 +135,9 @@ typedef char                                TCHAR, *PTCHAR, *PTSTR;
 #define IMG_FORMAT_PRINTF(x,y)
 #endif
 
+/*
+ * Cleanup request defines
+  */
 #define  CLEANUP_WITH_POLL             IMG_FALSE
 #define  FORCE_CLEANUP                 IMG_TRUE
 
@@ -118,4 +147,7 @@ typedef char                                TCHAR, *PTCHAR, *PTSTR;
 #define IMG_UNDEF      (~0UL)
 #endif
 
-#endif 
+#endif /* #if !defined (__IMG_DEFS_H__) */
+/*****************************************************************************
+ End of file (IMG_DEFS.H)
+*****************************************************************************/
index 2431786..7f5137e 100644 (file)
@@ -1,36 +1,54 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Global types for use by IMG APIs
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Defines type aliases for use by IMG APIs.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __IMG_TYPES_H__
 #define __IMG_TYPES_H__
 
+/* define all address space bit depths: */
+/* CPU virtual address space defaults to 32bits */
 #if !defined(IMG_ADDRSPACE_CPUVADDR_BITS)
 #define IMG_ADDRSPACE_CPUVADDR_BITS            32
 #endif
 
+/* Physical address space defaults to 32bits */
 #if !defined(IMG_ADDRSPACE_PHYSADDR_BITS)
 #define IMG_ADDRSPACE_PHYSADDR_BITS            32
 #endif
@@ -56,13 +74,13 @@ typedef signed long         IMG_INT32,      *IMG_PINT32;
        #define IMG_UINT32_MAX 0xFFFFFFFFUL
 #endif
 
-#if defined(USE_CODE)
+#if  defined(USE_CODE)
 
 typedef unsigned __int64       IMG_UINT64, *IMG_PUINT64;
 typedef __int64                                IMG_INT64,  *IMG_PINT64;
 
 #else
      #if ((defined(LINUX) || defined(__METAG)) || defined(__QNXNTO__))
#if defined(LINUX) || defined(__METAG) || defined (__QNXNTO__)
                typedef unsigned long long              IMG_UINT64,     *IMG_PUINT64;
                typedef long long                               IMG_INT64,      *IMG_PINT64;
        #else
@@ -71,6 +89,7 @@ typedef __int64                               IMG_INT64,  *IMG_PINT64;
 #endif
 
 #if !(defined(LINUX) && defined (__KERNEL__))
+/* Linux kernel mode does not use floating point */
 typedef float                  IMG_FLOAT,      *IMG_PFLOAT;
 typedef double                 IMG_DOUBLE, *IMG_PDOUBLE;
 #endif
@@ -101,21 +120,59 @@ typedef void**          IMG_HVOID,        * IMG_PHVOID;
 
 #define IMG_NULL        0 
 
+/* services/stream ID */
 typedef IMG_UINT32      IMG_SID;
 
 typedef IMG_UINT32      IMG_EVENTSID;
 
-#if defined(SUPPORT_SID_INTERFACE)
-       typedef IMG_SID IMG_S_HANDLE;
-#else
-       typedef IMG_HANDLE IMG_S_HANDLE;
-#endif
+/*
+ * Address types.
+ * All types used to refer to a block of memory are wrapped in structures
+ * to enforce some degree of type safety, i.e. a IMG_DEV_VIRTADDR cannot
+ * be assigned to a variable of type IMG_DEV_PHYADDR because they are not the
+ * same thing.
+ *
+ * There is an assumption that the system contains at most one non-cpu mmu,
+ * and a memory block is only mapped by the MMU once.
+ *
+ * Different devices could have offset views of the physical address space.
+ * 
+ */
+
+
+/*
+ *
+ * +------------+    +------------+      +------------+        +------------+
+ * |    CPU     |    |    DEV     |      |    DEV     |        |    DEV     |
+ * +------------+    +------------+      +------------+        +------------+
+ *       |                 |                   |                     |
+ *       | PVOID           |IMG_DEV_VIRTADDR   |IMG_DEV_VIRTADDR     |
+ *       |                 \-------------------/                     |
+ *       |                          |                                |
+ * +------------+             +------------+                         |     
+ * |    MMU     |             |    MMU     |                         |
+ * +------------+             +------------+                         | 
+ *       |                          |                                | 
+ *       |                          |                                |
+ *       |                          |                                |
+ *   +--------+                +---------+                      +--------+
+ *   | Offset |                | (Offset)|                      | Offset |
+ *   +--------+                +---------+                      +--------+    
+ *       |                          |                IMG_DEV_PHYADDR | 
+ *       |                          |                                |
+ *       |                          | IMG_DEV_PHYADDR                |
+ * +---------------------------------------------------------------------+ 
+ * |                         System Address bus                          |
+ * +---------------------------------------------------------------------+
+ *
+ */
 
 typedef IMG_PVOID IMG_CPU_VIRTADDR;
 
+/* device virtual address */
 typedef struct _IMG_DEV_VIRTADDR
 {
-       
+       /* device virtual addresses are 32bit for now */
        IMG_UINT32  uiAddr;
 #define IMG_CAST_TO_DEVVADDR_UINT(var)         (IMG_UINT32)(var)
        
@@ -123,16 +180,18 @@ typedef struct _IMG_DEV_VIRTADDR
 
 typedef IMG_UINT32 IMG_DEVMEM_SIZE_T;
 
+/* cpu physical address */
 typedef struct _IMG_CPU_PHYADDR
 {
-       
+       /* variable sized type (32,64) */
        IMG_UINTPTR_T uiAddr;
 } IMG_CPU_PHYADDR;
 
+/* device physical address */
 typedef struct _IMG_DEV_PHYADDR
 {
 #if IMG_ADDRSPACE_PHYSADDR_BITS == 32
-       
+       /* variable sized type (32,64) */
        IMG_UINTPTR_T uiAddr;
 #else
        IMG_UINT32 uiAddr;
@@ -140,12 +199,16 @@ typedef struct _IMG_DEV_PHYADDR
 #endif
 } IMG_DEV_PHYADDR;
 
+/* system physical address */
 typedef struct _IMG_SYS_PHYADDR
 {
-       
+       /* variable sized type (32,64) */
        IMG_UINTPTR_T uiAddr;
 } IMG_SYS_PHYADDR;
 
 #include "img_defs.h"
 
-#endif 
+#endif /* __IMG_TYPES_H__ */
+/******************************************************************************
+ End of file (img_types.h)
+******************************************************************************/
index 193b464..112e9ee 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PDUMP definitions header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    PDUMP definitions header
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #if !defined (__PDUMPDEFS_H__)
 #define __PDUMPDEFS_H__
 
@@ -104,5 +119,8 @@ typedef enum _PDUMP_POLL_OPERATOR
 } PDUMP_POLL_OPERATOR;
 
 
-#endif 
+#endif /* __PDUMPDEFS_H__ */
 
+/*****************************************************************************
+ End of file (pdumpdefs.h)
+*****************************************************************************/
index a9d082e..7e05666 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
-******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          PVR Debug Declarations
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provides debug functionality
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __PVR_DEBUG_H__
 #define __PVR_DEBUG_H__
 
@@ -38,32 +53,16 @@ extern "C" {
 #define PVR_MAX_DEBUG_MESSAGE_LEN      (512)
 
 /* These are privately used by pvr_debug, use the PVR_DBG_ defines instead */
-#define DBGPRIV_FATAL          0x01UL
-#define DBGPRIV_ERROR          0x02UL
-#define DBGPRIV_WARNING                0x04UL
-#define DBGPRIV_MESSAGE                0x08UL
-#define DBGPRIV_VERBOSE                0x10UL
-#define DBGPRIV_CALLTRACE      0x20UL
-#define DBGPRIV_ALLOC          0x40UL
-
-#define DBGPRIV_DBGDRV_MESSAGE 0x1000UL
-
-#define DBGPRIV_ALLLEVELS      (DBGPRIV_FATAL | DBGPRIV_ERROR | DBGPRIV_WARNING | DBGPRIV_MESSAGE | DBGPRIV_VERBOSE)
-
+#define DBGPRIV_FATAL                  0x01UL
+#define DBGPRIV_ERROR                  0x02UL
+#define DBGPRIV_WARNING                        0x04UL
+#define DBGPRIV_MESSAGE                        0x08UL
+#define DBGPRIV_VERBOSE                        0x10UL
+#define DBGPRIV_CALLTRACE              0x20UL
+#define DBGPRIV_ALLOC                  0x40UL
+#define DBGPRIV_DBGDRV_MESSAGE 0x80UL
 
-
-#define PVR_DBG_FATAL          DBGPRIV_FATAL,__FILE__, __LINE__
-#define PVR_DBG_ERROR          DBGPRIV_ERROR,__FILE__, __LINE__
-#define PVR_DBG_WARNING                DBGPRIV_WARNING,__FILE__, __LINE__
-#define PVR_DBG_MESSAGE                DBGPRIV_MESSAGE,__FILE__, __LINE__
-#define PVR_DBG_VERBOSE                DBGPRIV_VERBOSE,__FILE__, __LINE__
-#define PVR_DBG_CALLTRACE      DBGPRIV_CALLTRACE,__FILE__, __LINE__
-#define PVR_DBG_ALLOC          DBGPRIV_ALLOC,__FILE__, __LINE__
-
-/*
- *     Debug driver debugging
- */
-#define PVR_DBGDRIV_MESSAGE            DBGPRIV_DBGDRV_MESSAGE, "", 0
+#define DBGPRIV_DBGLEVEL_COUNT 8
 
 #if !defined(PVRSRV_NEED_PVR_ASSERT) && defined(DEBUG)
 #define PVRSRV_NEED_PVR_ASSERT
@@ -77,20 +76,49 @@ extern "C" {
 #define PVRSRV_NEED_PVR_TRACE
 #endif
 
-
 /* PVR_ASSERT() and PVR_DBG_BREAK handling */
 
 #if defined(PVRSRV_NEED_PVR_ASSERT)
 
-       #define PVR_ASSERT(EXPR) if (!(EXPR)) PVRSRVDebugAssertFail(__FILE__, __LINE__);
+#if defined(LINUX) && defined(__KERNEL__)
+/* In Linux kernel mode, use BUG() directly. This produces the correct
+   filename and line number in the panic message. */
+#define PVR_ASSERT(EXPR) do                                                                                    \
+       {                                                                                                                               \
+               if (!(EXPR))                                                                                            \
+               {                                                                                                                       \
+                       PVRSRVDebugPrintf(DBGPRIV_FATAL, __FILE__, __LINE__,    \
+                                                         "Debug assertion failed!");                   \
+                       BUG();                                                                                                  \
+               }                                                                                                                       \
+       } while (0)
+
+#else /* defined(LINUX) && defined(__KERNEL__) */
 
 IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVDebugAssertFail(const IMG_CHAR *pszFile,
                                                                                                           IMG_UINT32 ui32Line);
 
-                       #if defined(PVR_DBG_BREAK_ASSERT_FAIL)
-                               #define PVR_DBG_BREAK   PVRSRVDebugAssertFail("PVR_DBG_BREAK", 0)
+#if defined(LINUX)
+       #define PVR_ASSERT(EXPR) do                                                             \
+               {                                                                                                       \
+                       if (!(EXPR))                                                                    \
+                               PVRSRVDebugAssertFail(__FILE__, __LINE__);      \
+               } while (0)
+#else
+    #if defined (__QNXNTO__)
+           #define PVR_ASSERT(EXPR) if (!(EXPR)) PVRSRVDebugAssertFail(__FILE__, __LINE__);
+    #else
+           #define PVR_ASSERT(EXPR) if (!(EXPR)) PVRSRVDebugAssertFail(__FILE__, __LINE__)
+    #endif
+#endif
+
+#endif /* defined(LINUX) && defined(__KERNEL__) */
+
+
+                       #if defined(LINUX) && defined(__KERNEL__)
+                               #define PVR_DBG_BREAK BUG()
                        #else
-                               #define PVR_DBG_BREAK
+                               #define PVR_DBG_BREAK PVRSRVDebugAssertFail(__FILE__, __LINE__)
                        #endif
 
 #else  /* defined(PVRSRV_NEED_PVR_ASSERT) */
@@ -105,7 +133,66 @@ IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVDebugAssertFail(const IMG_CHAR *pszFile,
 
 #if defined(PVRSRV_NEED_PVR_DPF)
 
-       #define PVR_DPF(X)              PVRSRVDebugPrintf X
+#if defined(PVRSRV_NEW_PVR_DPF)
+
+       /* New logging mechanism */
+       #define PVR_DBG_FATAL           DBGPRIV_FATAL
+       #define PVR_DBG_ERROR           DBGPRIV_ERROR
+       #define PVR_DBG_WARNING         DBGPRIV_WARNING
+       #define PVR_DBG_MESSAGE         DBGPRIV_MESSAGE
+       #define PVR_DBG_VERBOSE         DBGPRIV_VERBOSE
+       #define PVR_DBG_CALLTRACE       DBGPRIV_CALLTRACE
+       #define PVR_DBG_ALLOC           DBGPRIV_ALLOC
+       #define PVR_DBGDRIV_MESSAGE     DBGPRIV_DBGDRV_MESSAGE
+
+       /* These levels are always on with PVRSRV_NEED_PVR_DPF */
+       #define __PVR_DPF_0x01UL(x...) PVRSRVDebugPrintf(DBGPRIV_FATAL, x)
+       #define __PVR_DPF_0x02UL(x...) PVRSRVDebugPrintf(DBGPRIV_ERROR, x)
+
+       /* Some are compiled out completely in release builds */
+#if defined(DEBUG)
+       #define __PVR_DPF_0x04UL(x...) PVRSRVDebugPrintf(DBGPRIV_WARNING, x)
+       #define __PVR_DPF_0x08UL(x...) PVRSRVDebugPrintf(DBGPRIV_MESSAGE, x)
+       #define __PVR_DPF_0x10UL(x...) PVRSRVDebugPrintf(DBGPRIV_VERBOSE, x)
+       #define __PVR_DPF_0x20UL(x...) PVRSRVDebugPrintf(DBGPRIV_CALLTRACE, x)
+       #define __PVR_DPF_0x40UL(x...) PVRSRVDebugPrintf(DBGPRIV_ALLOC, x)
+       #define __PVR_DPF_0x80UL(x...) PVRSRVDebugPrintf(DBGPRIV_DBGDRV_MESSAGE, x)
+#else
+       #define __PVR_DPF_0x04UL(x...)
+       #define __PVR_DPF_0x08UL(x...)
+       #define __PVR_DPF_0x10UL(x...)
+       #define __PVR_DPF_0x20UL(x...)
+       #define __PVR_DPF_0x40UL(x...)
+       #define __PVR_DPF_0x80UL(x...)
+#endif
+
+       /* Translate the different log levels to separate macros
+        * so they can each be compiled out.
+        */
+#if defined(DEBUG)
+       #define __PVR_DPF(lvl, x...) __PVR_DPF_ ## lvl (__FILE__, __LINE__, x)
+#else
+       #define __PVR_DPF(lvl, x...) __PVR_DPF_ ## lvl ("", 0, x)
+#endif
+
+       /* Get rid of the double bracketing */
+       #define PVR_DPF(x) __PVR_DPF x
+
+#else /* defined(PVRSRV_NEW_PVR_DPF) */
+
+       /* Old logging mechanism */
+       #define PVR_DBG_FATAL           DBGPRIV_FATAL,__FILE__, __LINE__
+       #define PVR_DBG_ERROR           DBGPRIV_ERROR,__FILE__, __LINE__
+       #define PVR_DBG_WARNING         DBGPRIV_WARNING,__FILE__, __LINE__
+       #define PVR_DBG_MESSAGE         DBGPRIV_MESSAGE,__FILE__, __LINE__
+       #define PVR_DBG_VERBOSE         DBGPRIV_VERBOSE,__FILE__, __LINE__
+       #define PVR_DBG_CALLTRACE       DBGPRIV_CALLTRACE,__FILE__, __LINE__
+       #define PVR_DBG_ALLOC           DBGPRIV_ALLOC,__FILE__, __LINE__
+       #define PVR_DBGDRIV_MESSAGE     DBGPRIV_DBGDRV_MESSAGE, "", 0
+
+       #define PVR_DPF(X)                      PVRSRVDebugPrintf X
+
+#endif /* defined(PVRSRV_NEW_PVR_DPF) */
 
 IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVDebugPrintf(IMG_UINT32 ui32DebugLevel,
                                                                                                   const IMG_CHAR *pszFileName,
index 3dd5845..267c7b6 100644 (file)
@@ -1,31 +1,48 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Module Author and License.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef        _PVRMODULE_H_
 #define        _PVRMODULE_H_
+
 MODULE_AUTHOR("Imagination Technologies Ltd. <gpl-support@imgtec.com>");
-MODULE_LICENSE("GPL");
-#endif 
+MODULE_LICENSE("Dual MIT/GPL");
+
+#endif /* _PVRMODULE_H_ */
index 5f78678..01212ad 100644 (file)
@@ -1,38 +1,46 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
-
-
-
-
-
-
-
+/*************************************************************************/ /*!
+@File
+@Title          Version numbers and strings.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Version numbers and strings for PVR Consumer services
+                components.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _PVRVERSION_H_
 #define _PVRVERSION_H_
 #define PVR_STR2(X) PVR_STR(X)
 
 #define PVRVERSION_MAJ               1
-#define PVRVERSION_MIN               7
-#define PVRVERSION_BRANCH            17
+#define PVRVERSION_MIN               9
+#define PVRVERSION_BRANCH            19
 
 #define PVRVERSION_FAMILY           "sgxddk"
-#define PVRVERSION_BRANCHNAME       "1.7"
-#define PVRVERSION_BUILD             867897
-#define PVRVERSION_BSCONTROL        "CustomerTI_OMAP4430_Linux_GPL"
+#define PVRVERSION_BRANCHNAME       "1.9.RC2"
+#define PVRVERSION_BUILD             2139099
+#define PVRVERSION_BSCONTROL        "SGX_DDK_Linux_CustomerTI"
 
-#define PVRVERSION_STRING           "CustomerTI_OMAP4430_Linux_GPL sgxddk 17 1.7@" PVR_STR2(PVRVERSION_BUILD)
-#define PVRVERSION_STRING_SHORT     "1.7@" PVR_STR2(PVRVERSION_BUILD)
+#define PVRVERSION_STRING           "SGX_DDK_Linux_CustomerTI sgxddk 19 1.9.RC2@" PVR_STR2(PVRVERSION_BUILD)
+#define PVRVERSION_STRING_SHORT     "1.9.RC2@" PVR_STR2(PVRVERSION_BUILD)
 
 #define COPYRIGHT_TXT               "Copyright (c) Imagination Technologies Ltd. All Rights Reserved."
 
-#define PVRVERSION_BUILD_HI          86
-#define PVRVERSION_BUILD_LO          7897
+#define PVRVERSION_BUILD_HI          213
+#define PVRVERSION_BUILD_LO          9099
 #define PVRVERSION_STRING_NUMERIC    PVR_STR2(PVRVERSION_MAJ) "." PVR_STR2(PVRVERSION_MIN) "." PVR_STR2(PVRVERSION_BUILD_HI) "." PVR_STR2(PVRVERSION_BUILD_LO)
 
-#endif 
+#endif /* _PVRVERSION_H_ */
index cd672d1..a0b5986 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Services API Header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Exported services API details
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __SERVICES_H__
 #define __SERVICES_H__
@@ -36,14 +52,33 @@ extern "C" {
 #include "pdumpdefs.h"
 
 
+/* The comment below is the front page for code-generated doxygen documentation */
+/*!
+ ******************************************************************************
+ @mainpage
+ This document details the APIs and implementation of the Consumer Services.
+ It is intended to be used in conjunction with the Consumer Services
+ Software Architectural Specification and the Consumer Services Software
+ Functional Specification.
+ *****************************************************************************/
+
+/******************************************************************************
+ *     #defines
+ *****************************************************************************/
+
+/* 4k page size definition */
 #define PVRSRV_4K_PAGE_SIZE            4096UL
 
-#define PVRSRV_MAX_CMD_SIZE            1024
+#define PVRSRV_MAX_CMD_SIZE            1024/*!< max size in bytes of a command */
 
-#define PVRSRV_MAX_DEVICES             16      
+#define PVRSRV_MAX_DEVICES             16      /*!< Largest supported number of devices on the system */
 
 #define EVENTOBJNAME_MAXLENGTH (50)
 
+/*
+       Flags associated with memory allocation
+       (bits 0-11)
+*/
 #define PVRSRV_MEM_READ                                                (1U<<0)
 #define PVRSRV_MEM_WRITE                                       (1U<<1)
 #define PVRSRV_MEM_CACHE_CONSISTENT                    (1U<<2)
@@ -58,6 +93,10 @@ extern "C" {
 #define PVRSRV_MEM_EXPORTED                                    (1U<<11)
 
 
+/*
+       Heap Attribute flags
+       (bits 12-23)
+*/
 #define PVRSRV_HAP_CACHED                                      (1U<<12)
 #define PVRSRV_HAP_UNCACHED                                    (1U<<13)
 #define PVRSRV_HAP_WRITECOMBINE                                (1U<<14)
@@ -73,51 +112,113 @@ extern "C" {
                                             |PVRSRV_HAP_FROM_EXISTING_PROCESS \
                                             |PVRSRV_HAP_NO_CPU_VIRTUAL)
 
+/*
+       Allows user allocations to override heap attributes
+       (Bits shared with heap flags)
+*/
 #define PVRSRV_MEM_CACHED                                      PVRSRV_HAP_CACHED
 #define PVRSRV_MEM_UNCACHED                                    PVRSRV_HAP_UNCACHED
 #define PVRSRV_MEM_WRITECOMBINE                                PVRSRV_HAP_WRITECOMBINE
 
+/*
+       Backing store flags (defined internally)
+       (bits 24-26)
+*/
 #define PVRSRV_MEM_BACKINGSTORE_FIELD_SHIFT    (24)
 
+/*
+       Per allocation/mapping flags
+       (bits 27-30)
+ */
 #define PVRSRV_MAP_NOUSERVIRTUAL            (1UL<<27)
 #define PVRSRV_MEM_XPROC                                       (1U<<28)
-
-#define PVRSRV_NO_CONTEXT_LOSS                                 0               
-#define PVRSRV_SEVERE_LOSS_OF_CONTEXT                  1               
-#define PVRSRV_PRE_STATE_CHANGE_MASK                   0x80    
-
-
-#define PVRSRV_DEFAULT_DEV_COOKIE                      (1)      
-
-
-#define PVRSRV_MISC_INFO_TIMER_PRESENT                         (1U<<0)
-#define PVRSRV_MISC_INFO_CLOCKGATE_PRESENT                     (1U<<1)
-#define PVRSRV_MISC_INFO_MEMSTATS_PRESENT                      (1U<<2)
-#define PVRSRV_MISC_INFO_GLOBALEVENTOBJECT_PRESENT     (1U<<3)
-#define PVRSRV_MISC_INFO_DDKVERSION_PRESENT                    (1U<<4)
-#define PVRSRV_MISC_INFO_CPUCACHEOP_PRESENT                    (1U<<5)
-#define PVRSRV_MISC_INFO_FREEMEM_PRESENT                       (1U<<6)
-
-#define PVRSRV_MISC_INFO_RESET_PRESENT                         (1U<<31)
-
+#define PVRSRV_MEM_ION                                         (1U<<29)
+#define PVRSRV_MEM_ALLOCATENONCACHEDMEM                (1UL<<30)
+
+/*
+       Internal allocation/mapping flags
+       (bit 31)
+*/
+#define PVRSRV_MEM_SPARSE                                      (1U<<31)
+
+
+/*
+ * How much context we lose on a (power) mode change
+ */
+#define PVRSRV_NO_CONTEXT_LOSS                                 0               /*!< Do not lose state on power down */
+#define PVRSRV_SEVERE_LOSS_OF_CONTEXT                  1               /*!< lose state on power down */
+#define PVRSRV_PRE_STATE_CHANGE_MASK                   0x80    /*!< power state change mask */
+
+
+/*
+ * Device cookie defines
+ */
+#define PVRSRV_DEFAULT_DEV_COOKIE                      (1)      /*!< default device cookie */
+
+
+/*
+ * Misc Info. present flags
+ */
+#define PVRSRV_MISC_INFO_TIMER_PRESENT                                 (1U<<0)
+#define PVRSRV_MISC_INFO_CLOCKGATE_PRESENT                             (1U<<1)
+#define PVRSRV_MISC_INFO_MEMSTATS_PRESENT                              (1U<<2)
+#define PVRSRV_MISC_INFO_GLOBALEVENTOBJECT_PRESENT             (1U<<3)
+#define PVRSRV_MISC_INFO_DDKVERSION_PRESENT                            (1U<<4)
+#define PVRSRV_MISC_INFO_CPUCACHEOP_PRESENT                            (1U<<5)
+#define PVRSRV_MISC_INFO_FREEMEM_PRESENT                               (1U<<6)
+#define PVRSRV_MISC_INFO_GET_REF_COUNT_PRESENT                 (1U<<7)
+#define PVRSRV_MISC_INFO_GET_PAGE_SIZE_PRESENT                 (1U<<8)
+#define PVRSRV_MISC_INFO_FORCE_SWAP_TO_SYSTEM_PRESENT  (1U<<9)
+
+#define PVRSRV_MISC_INFO_RESET_PRESENT                                 (1U<<31)
+
+/* PDUMP defines */
 #define PVRSRV_PDUMP_MAX_FILENAME_SIZE                 20
 #define PVRSRV_PDUMP_MAX_COMMENT_SIZE                  200
 
 
+/*
+       Flags for PVRSRVChangeDeviceMemoryAttributes call.
+*/
 #define PVRSRV_CHANGEDEVMEM_ATTRIBS_CACHECOHERENT              0x00000001
 
+/*
+       Flags for PVRSRVMapExtMemory and PVRSRVUnmapExtMemory
+       ALTERNATEVA             -       Used when mapping multiple virtual addresses to the same physical address. Set this flag on extra maps.
+       PHYSCONTIG              -       Physical pages are contiguous (unused)
+*/
 #define PVRSRV_MAPEXTMEMORY_FLAGS_ALTERNATEVA                  0x00000001
 #define PVRSRV_MAPEXTMEMORY_FLAGS_PHYSCONTIG                   0x00000002
 
+/*
+       Flags for PVRSRVModifySyncOps
+       WO_INC          -       Used to increment "WriteOpsPending/complete of sync info"
+       RO_INC          -       Used to increment "ReadOpsPending/complete of sync info"
+*/
 #define PVRSRV_MODIFYSYNCOPS_FLAGS_WO_INC                      0x00000001
 #define PVRSRV_MODIFYSYNCOPS_FLAGS_RO_INC                      0x00000002
 
+/*
+       Flags for Services connection.
+       Allows to define per-client policy for Services
+*/
 #define SRV_FLAGS_PERSIST              0x1
 #define SRV_FLAGS_PDUMP_ACTIVE 0x2
 
+/*
+       Pdump flags which are accessible to Services clients
+*/
 #define PVRSRV_PDUMP_FLAGS_CONTINUOUS          0x1
 
 
+/******************************************************************************
+ * Enums
+ *****************************************************************************/
+
+/*!
+ ******************************************************************************
+ * List of known device types.
+ *****************************************************************************/
 typedef enum _PVRSRV_DEVICE_TYPE_
 {
        PVRSRV_DEVICE_TYPE_UNKNOWN                      = 0 ,
@@ -133,7 +234,7 @@ typedef enum _PVRSRV_DEVICE_TYPE_
 
        PVRSRV_DEVICE_TYPE_VGX                          = 8,
 
-       
+       /* 3rd party devices take ext type */
        PVRSRV_DEVICE_TYPE_EXT                          = 9,
 
     PVRSRV_DEVICE_TYPE_LAST             = 9,
@@ -146,8 +247,13 @@ typedef enum _PVRSRV_DEVICE_TYPE_
 #define HEAP_IDX( _heap_id_ )                          ( (_heap_id_)&((1<<24) - 1 ) )
 #define HEAP_DEV( _heap_id_ )                          ( (_heap_id_)>>24 )
 
+/* common undefined heap ID define */
 #define PVRSRV_UNDEFINED_HEAP_ID                       (~0LU)
 
+/*!
+ ******************************************************************************
+ * User Module type
+ *****************************************************************************/
 typedef enum
 {
        IMG_EGL                         = 0x00000001,
@@ -175,6 +281,10 @@ typedef enum
 
 #define APPHINT_MAX_STRING_SIZE        256
 
+/*!
+ ******************************************************************************
+ * IMG data types
+ *****************************************************************************/
 typedef enum
 {
        IMG_STRING_TYPE         = 1,
@@ -185,145 +295,181 @@ typedef enum
 }IMG_DATA_TYPE;
 
 
+/******************************************************************************
+ * Structure definitions.
+ *****************************************************************************/
+
+/*!
+ * Forward declaration
+ */
 typedef struct _PVRSRV_DEV_DATA_ *PPVRSRV_DEV_DATA;
 
+/*!
+ ******************************************************************************
+ * Device identifier structure
+ *****************************************************************************/
 typedef struct _PVRSRV_DEVICE_IDENTIFIER_
 {
-       PVRSRV_DEVICE_TYPE              eDeviceType;            
-       PVRSRV_DEVICE_CLASS             eDeviceClass;           
-       IMG_UINT32                              ui32DeviceIndex;        
-       IMG_CHAR                                *pszPDumpDevName;       
-       IMG_CHAR                                *pszPDumpRegName;       
+       PVRSRV_DEVICE_TYPE              eDeviceType;            /*!< Identifies the type of the device */
+       PVRSRV_DEVICE_CLASS             eDeviceClass;           /*!< Identifies more general class of device - display/3d/mpeg etc */
+       IMG_UINT32                              ui32DeviceIndex;        /*!< Index of the device within the system */
+       IMG_CHAR                                *pszPDumpDevName;       /*!< Pdump memory bank name */
+       IMG_CHAR                                *pszPDumpRegName;       /*!< Pdump register bank name */
 
 } PVRSRV_DEVICE_IDENTIFIER;
 
 
+/******************************************************************************
+ * Client dev info
+ ******************************************************************************
+ */
 typedef struct _PVRSRV_CLIENT_DEV_DATA_
 {
-       IMG_UINT32              ui32NumDevices;                         
-       PVRSRV_DEVICE_IDENTIFIER asDevID[PVRSRV_MAX_DEVICES];           
-       PVRSRV_ERROR    (*apfnDevConnect[PVRSRV_MAX_DEVICES])(PPVRSRV_DEV_DATA);        
-       PVRSRV_ERROR    (*apfnDumpTrace[PVRSRV_MAX_DEVICES])(PPVRSRV_DEV_DATA);         
+       IMG_UINT32              ui32NumDevices;                         /*!< Number of services-managed devices connected */
+       PVRSRV_DEVICE_IDENTIFIER asDevID[PVRSRV_MAX_DEVICES];           /*!< Device identifiers */
+       PVRSRV_ERROR    (*apfnDevConnect[PVRSRV_MAX_DEVICES])(PPVRSRV_DEV_DATA);        /*< device-specific connection callback */
+       PVRSRV_ERROR    (*apfnDumpTrace[PVRSRV_MAX_DEVICES])(PPVRSRV_DEV_DATA);         /*!< device-specific debug trace callback */
 
 } PVRSRV_CLIENT_DEV_DATA;
 
 
+/*!
+ ******************************************************************************
+ * Kernel Services connection structure
+ *****************************************************************************/
 typedef struct _PVRSRV_CONNECTION_
 {
-       IMG_HANDLE hServices;                                   
-       IMG_UINT32 ui32ProcessID;                               
-       PVRSRV_CLIENT_DEV_DATA  sClientDevData; 
-       IMG_UINT32 ui32SrvFlags;                                
+       IMG_HANDLE hServices;                                   /*!< UM IOCTL handle */
+       IMG_UINT32 ui32ProcessID;                               /*!< Process ID for resource locking */
+       PVRSRV_CLIENT_DEV_DATA  sClientDevData; /*!< Client device data */
+       IMG_UINT32 ui32SrvFlags;                                /*!< Per-client Services flags */
 }PVRSRV_CONNECTION;
 
 
+/*!
+ ******************************************************************************
+ * This structure allows the user mode glue code to have an OS independent
+ * set of prototypes.
+ *****************************************************************************/
 typedef struct _PVRSRV_DEV_DATA_
 {
-       IMG_CONST PVRSRV_CONNECTION      *psConnection; 
+       IMG_CONST PVRSRV_CONNECTION      *psConnection; /*!< Services connection info */
 #if defined (SUPPORT_SID_INTERFACE)
-       IMG_SID                 hDevCookie;                             
+       IMG_SID                 hDevCookie;                             /*!< Dev cookie */
 #else
-       IMG_HANDLE                      hDevCookie;                             
+       IMG_HANDLE                      hDevCookie;                             /*!< Dev cookie */
 #endif
 
 } PVRSRV_DEV_DATA;
 
+/*!
+ ******************************************************************************
+ * address:value update structure
+ *****************************************************************************/
 typedef struct _PVRSRV_MEMUPDATE_
 {
-       IMG_UINT32                      ui32UpdateAddr;         
-       IMG_UINT32                      ui32UpdateVal;          
+       IMG_UINT32                      ui32UpdateAddr;         /*!< Address */
+       IMG_UINT32                      ui32UpdateVal;          /*!< value */
 } PVRSRV_MEMUPDATE;
 
+/*!
+ ******************************************************************************
+ * address:value register structure
+ *****************************************************************************/
 typedef struct _PVRSRV_HWREG_
 {
-       IMG_UINT32                      ui32RegAddr;    
-       IMG_UINT32                      ui32RegVal;             
+       IMG_UINT32                      ui32RegAddr;    /*!< Address */
+       IMG_UINT32                      ui32RegVal;             /*!< value */
 } PVRSRV_HWREG;
 
+/*!
+ ******************************************************************************
+ * Implementation details for memory handling
+ *****************************************************************************/
 typedef struct _PVRSRV_MEMBLK_
 {
-       IMG_DEV_VIRTADDR        sDevVirtAddr;                   
-       IMG_HANDLE                      hOSMemHandle;                   
-       IMG_HANDLE                      hOSWrapMem;                             
-       IMG_HANDLE                      hBuffer;                                
-       IMG_HANDLE                      hResItem;                               
+       IMG_DEV_VIRTADDR        sDevVirtAddr;                   /*!< Address of the memory in the IMG MMUs address space */
+       IMG_HANDLE                      hOSMemHandle;                   /*!< Stores the underlying memory allocation handle */
+       IMG_HANDLE                      hOSWrapMem;                             /*!< FIXME: better way to solve this problem */
+       IMG_HANDLE                      hBuffer;                                /*!< Stores the BM_HANDLE for the underlying memory management */
+       IMG_HANDLE                      hResItem;                               /*!< handle to resource item for allocate */
        IMG_SYS_PHYADDR         *psIntSysPAddr;
 
 } PVRSRV_MEMBLK;
 
+/*!
+ ******************************************************************************
+ * Memory Management (externel interface)
+ *****************************************************************************/
 typedef struct _PVRSRV_KERNEL_MEM_INFO_ *PPVRSRV_KERNEL_MEM_INFO;
 
 typedef struct _PVRSRV_CLIENT_MEM_INFO_
 {
-       
+       /* CPU Virtual Address */
        IMG_PVOID                               pvLinAddr;
 
-       
+       /* CPU Virtual Address (for kernel mode) */
        IMG_PVOID                               pvLinAddrKM;
 
-       
+       /* Device Virtual Address */
        IMG_DEV_VIRTADDR                sDevVAddr;
 
-       
-
-
-
-
-       IMG_CPU_PHYADDR                 sCpuPAddr;
-
-       
+       /* allocation flags */
        IMG_UINT32                              ui32Flags;
 
-       
-
-
+       /* client allocation flags */
        IMG_UINT32                              ui32ClientFlags;
 
-       
+       /* allocation size in bytes */
        IMG_SIZE_T                              uAllocSize;
 
 
-       
+       /* ptr to associated client sync info - NULL if no sync */
        struct _PVRSRV_CLIENT_SYNC_INFO_        *psClientSyncInfo;
 
 #if defined (SUPPORT_SID_INTERFACE)
-       
+       /* handle to client mapping data (OS specific) */
        IMG_SID                                                         hMappingInfo;
 
-       
+       /* handle to kernel mem info */
        IMG_SID                                                         hKernelMemInfo;
 
-       
+       /* resman handle for UM mapping clean-up */
        IMG_SID                                                         hResItem;
 #else
-       
+       /* handle to client mapping data (OS specific) */
        IMG_HANDLE                                                      hMappingInfo;
 
-       
+       /* handle to kernel mem info */
        IMG_HANDLE                                                      hKernelMemInfo;
 
-       
+       /* resman handle for UM mapping clean-up */
        IMG_HANDLE                                                      hResItem;
 #endif
 
 #if defined(SUPPORT_MEMINFO_IDS)
        #if !defined(USE_CODE)
-       
+       /* Globally unique "stamp" for allocation (not re-used until wrap) */
        IMG_UINT64                                                      ui64Stamp;
-       #else 
+       #else /* !defined(USE_CODE) */
        IMG_UINT32                                                      dummy1;
        IMG_UINT32                                                      dummy2;
-       #endif 
-#endif 
-
-       
-
+       #endif /* !defined(USE_CODE) */
+#endif /* defined(SUPPORT_MEMINFO_IDS) */
 
+       /*
+               ptr to next mem info
+               D3D uses psNext for mid-scene texture reload.
+       */
        struct _PVRSRV_CLIENT_MEM_INFO_         *psNext;
 
 } PVRSRV_CLIENT_MEM_INFO, *PPVRSRV_CLIENT_MEM_INFO;
 
 
+/*!
+ ******************************************************************************
+ * Memory Heap Information
+ *****************************************************************************/
 #define PVRSRV_MAX_CLIENT_HEAPS (32)
 typedef struct _PVRSRV_HEAP_INFO_
 {
@@ -342,11 +488,14 @@ typedef struct _PVRSRV_HEAP_INFO_
 
 
 
+/*
+       Event Object information structure
+*/
 typedef struct _PVRSRV_EVENTOBJECT_
 {
-       
+       /* globally unique name of the event object */
        IMG_CHAR        szName[EVENTOBJNAME_MAXLENGTH];
-       
+       /* kernel specific handle for the event object */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID     hOSEventKM;
 #else
@@ -355,6 +504,9 @@ typedef struct _PVRSRV_EVENTOBJECT_
 
 } PVRSRV_EVENTOBJECT;
 
+/*
+       Cache operation type
+*/
 typedef enum
 {
        PVRSRV_MISC_INFO_CPUCACHEOP_NONE = 0,
@@ -362,12 +514,16 @@ typedef enum
        PVRSRV_MISC_INFO_CPUCACHEOP_FLUSH
 } PVRSRV_MISC_INFO_CPUCACHEOP_TYPE;
 
+/*!
+ ******************************************************************************
+ * Structure to retrieve misc. information from services
+ *****************************************************************************/
 typedef struct _PVRSRV_MISC_INFO_
 {
-       IMG_UINT32      ui32StateRequest;               
-       IMG_UINT32      ui32StatePresent;               
+       IMG_UINT32      ui32StateRequest;               /*!< requested State Flags */
+       IMG_UINT32      ui32StatePresent;               /*!< Present/Valid State Flags */
 
-       
+       /*!< SOC Timer register */
        IMG_VOID        *pvSOCTimerRegisterKM;
        IMG_VOID        *pvSOCTimerRegisterUM;
 #if defined (SUPPORT_SID_INTERFACE)
@@ -378,58 +534,90 @@ typedef struct _PVRSRV_MISC_INFO_
        IMG_HANDLE      hSOCTimerRegisterMappingInfo;
 #endif
 
-       
+       /*!< SOC Clock Gating registers */
        IMG_VOID        *pvSOCClockGateRegs;
        IMG_UINT32      ui32SOCClockGateRegsSize;
 
-       
+       /* Memory Stats/DDK version string depending on ui32StateRequest flags */
        IMG_CHAR        *pszMemoryStr;
        IMG_UINT32      ui32MemoryStrLen;
 
-       
-       PVRSRV_EVENTOBJECT      sGlobalEventObject;
+       /* global event object */
+       PVRSRV_EVENTOBJECT      sGlobalEventObject;//FIXME: should be private to services
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_EVENTSID            hOSGlobalEvent;
 #else
        IMG_HANDLE                      hOSGlobalEvent;
 #endif
 
-       
+       /* Note: add misc. items as required */
        IMG_UINT32      aui32DDKVersion[4];
 
-       
+       /*!< CPU cache flush controls: */
        struct
        {
-               
+               /*!< Defer the CPU cache op to the next HW op to be submitted (else flush now) */
                IMG_BOOL bDeferOp;
 
-               
+               /*!< Type of cache operation to perform */
                PVRSRV_MISC_INFO_CPUCACHEOP_TYPE eCacheOpType;
 
-               
+               /* This union is a bit unsightly. We need it because we'll use the psMemInfo
+                * directly in the srvclient PVRSRVGetMiscInfo code, and then convert it
+                * to a kernel meminfo if required. Try to not waste space.
+                */
 #if !defined (SUPPORT_SID_INTERFACE)
                union
                {
-                       
+                       /*!< Input client meminfo (UM side) */
                        PVRSRV_CLIENT_MEM_INFO *psClientMemInfo;
 
-                       
+                       /*!< Output kernel meminfo (Bridge+KM side) */
                        struct _PVRSRV_KERNEL_MEM_INFO_ *psKernelMemInfo;
                } u;
 #endif
 
-               
+               /*!< Offset in MemInfo to start cache op */
                IMG_VOID *pvBaseVAddr;
 
-               
+               /*!< Length of range to perform cache op  */
                IMG_UINT32      ui32Length;
        } sCacheOpCtl;
+
+       /*!< Meminfo refcount controls: */
+       struct
+       {
+               /* This union is a bit unsightly. We need it because we'll use the psMemInfo
+                * directly in the srvclient PVRSRVGetMiscInfo code, and then convert it
+                * to a kernel meminfo if required. Try to not waste space.
+                */
+#if !defined(SUPPORT_SID_INTERFACE)
+               union
+               {
+                       /*!< Input client meminfo (UM side) */
+                       PVRSRV_CLIENT_MEM_INFO *psClientMemInfo;
+
+                       /*!< Output kernel meminfo (Bridge+KM side) */
+                       struct _PVRSRV_KERNEL_MEM_INFO_ *psKernelMemInfo;
+               } u;
+#endif
+
+               /*!< Resulting refcount */
+               IMG_UINT32 ui32RefCount;
+       } sGetRefCountCtl;
+
+       IMG_UINT32 ui32PageSize;
 } PVRSRV_MISC_INFO;
 
+/*!
+ ******************************************************************************
+ * Synchronisation token
+ *****************************************************************************/
 typedef struct _PVRSRV_SYNC_TOKEN_
 {
-       
-
+       /* This token is supposed to be passed around as an opaque object
+          - caller should not rely on the internal fields staying the same.
+          The fields are hidden in sPrivate in order to reinforce this. */
        struct
        {
 #if defined (SUPPORT_SID_INTERFACE)
@@ -439,20 +627,29 @@ typedef struct _PVRSRV_SYNC_TOKEN_
 #endif
                IMG_UINT32 ui32ReadOpsPendingSnapshot;
                IMG_UINT32 ui32WriteOpsPendingSnapshot;
+               IMG_UINT32 ui32ReadOps2PendingSnapshot;
        } sPrivate;
 } PVRSRV_SYNC_TOKEN;
 
 
+/******************************************************************************
+ * PVR Client Event handling in Services
+ *****************************************************************************/
 typedef enum _PVRSRV_CLIENT_EVENT_
 {
        PVRSRV_CLIENT_EVENT_HWTIMEOUT = 0,
 } PVRSRV_CLIENT_EVENT;
 
+typedef IMG_VOID (*PFN_QUEUE_COMMAND_COMPLETE)(IMG_HANDLE hCallbackData);
+
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVClientEvent(IMG_CONST PVRSRV_CLIENT_EVENT eEvent,
                                                                                        PVRSRV_DEV_DATA *psDevData,
                                                                                        IMG_PVOID pvData);
 
+/******************************************************************************
+ * PVR Services API prototypes.
+ *****************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVConnect(PVRSRV_CONNECTION **ppsConnection, IMG_UINT32 ui32SrvFlags);
 
@@ -474,16 +671,6 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfo (IMG_CONST PVRSRV_CONNECTION *psConn
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVReleaseMiscInfo (IMG_CONST PVRSRV_CONNECTION *psConnection, PVRSRV_MISC_INFO *psMiscInfo);
 
-#if 1
-IMG_IMPORT
-IMG_UINT32 ReadHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset);
-
-IMG_IMPORT
-IMG_VOID WriteHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset, IMG_UINT32 ui32Value);
-
-IMG_IMPORT IMG_VOID WriteHWRegs(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Count, PVRSRV_HWREG *psHWRegs);
-#endif
-
 IMG_IMPORT
 PVRSRV_ERROR PVRSRVPollForValue ( const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -497,6 +684,7 @@ PVRSRV_ERROR PVRSRVPollForValue ( const PVRSRV_CONNECTION *psConnection,
                                                        IMG_UINT32 ui32Waitus,
                                                        IMG_UINT32 ui32Tries);
 
+/* memory APIs */
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateDeviceMemContext(IMG_CONST PVRSRV_DEV_DATA *psDevData,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -510,10 +698,11 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateDeviceMemContext(IMG_CONST PVRSRV_DEV_DATA
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyDeviceMemContext(IMG_CONST PVRSRV_DEV_DATA *psDevData,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                                       IMG_SID                         hDevMemContext);
+                                                                                       IMG_SID                         hDevMemContext
 #else
-                                                                                       IMG_HANDLE                      hDevMemContext);
+                                                                                       IMG_HANDLE                      hDevMemContext
 #endif
+       );
 
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapInfo(IMG_CONST PVRSRV_DEV_DATA *psDevData,
@@ -536,6 +725,20 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapInfo(IMG_CONST PVRSRV_DEV_DATA *
 #endif
 
 
+IMG_IMPORT
+PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocDeviceMem2(IMG_CONST PVRSRV_DEV_DATA      *psDevData,
+#if defined (SUPPORT_SID_INTERFACE)
+                                                                       IMG_SID                 hDevMemHeap,
+#else
+                                                                       IMG_HANDLE              hDevMemHeap,
+#endif
+                                                                       IMG_UINT32              ui32Attribs,
+                                                                       IMG_SIZE_T              ui32Size,
+                                                                       IMG_SIZE_T              ui32Alignment,
+                                                                       IMG_PVOID               pvPrivData,
+                                                                       IMG_UINT32              ui32PrivDataLength,
+                                                                       PVRSRV_CLIENT_MEM_INFO  **ppsMemInfo);
+
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocDeviceMem(IMG_CONST PVRSRV_DEV_DATA       *psDevData,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -556,10 +759,11 @@ IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVExportDeviceMem(IMG_CONST PVRSRV_DEV_DATA      *psDevData,
                                                                                                PVRSRV_CLIENT_MEM_INFO          *psMemInfo,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                                               IMG_SID                                         *phMemInfo);
+                                                                                               IMG_SID                                         *phMemInfo
 #else
-                                                                                               IMG_HANDLE                                      *phMemInfo);
+                                                                                               IMG_HANDLE                                      *phMemInfo
 #endif
+       );
 
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVReserveDeviceVirtualMem(IMG_CONST PVRSRV_DEV_DATA *psDevData,
@@ -665,7 +869,43 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceMemory2(IMG_CONST PVRSRV_DEV_DATA *psDe
                                                                                                 IMG_HANDLE                                     hDstDevMemHeap,
 #endif
                                                                                                 PVRSRV_CLIENT_MEM_INFO         **ppsDstMemInfo);
-#endif 
+#endif /* defined(LINUX) */
+
+#if defined(SUPPORT_ION)
+PVRSRV_ERROR PVRSRVMapIonHandle(const PVRSRV_DEV_DATA *psDevData,
+#if defined (SUPPORT_SID_INTERFACE)
+                                                                IMG_SID    hDevMemContext,
+#else
+                                                                IMG_HANDLE hDevMemContext,
+#endif
+                                                               IMG_INT32 uiFD,
+                                                               IMG_UINT32 uiSize,
+                                                               IMG_UINT32 ui32Attribs,
+                                                               PVRSRV_CLIENT_MEM_INFO **ppsMemInfo);
+
+PVRSRV_ERROR PVRSRVUnmapIonHandle(const PVRSRV_DEV_DATA *psDevData,
+                                                                 PVRSRV_CLIENT_MEM_INFO *psMemInfo);
+#endif /* defined (SUPPORT_ION) */
+
+
+IMG_IMPORT
+PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocDeviceMemSparse(const PVRSRV_DEV_DATA *psDevData,
+#if defined (SUPPORT_SID_INTERFACE)
+                                                                                                       IMG_SID  hDevMemHeap,
+#else
+                                                                                                       IMG_HANDLE hDevMemHeap,
+#endif
+                                                                                                       IMG_UINT32 ui32Attribs,
+                                                                                                       IMG_SIZE_T uAlignment,
+                                                                                                       IMG_UINT32 ui32ChunkSize,
+                                                                                                       IMG_UINT32 ui32NumVirtChunks,
+                                                                                                       IMG_UINT32 ui32NumPhysChunks,
+                                                                                                       IMG_BOOL *pabMapChunk,
+                                                                                                       PVRSRV_CLIENT_MEM_INFO **ppsMemInfo);
+
+/******************************************************************************
+ * PVR Allocation Synchronisation Functionality...
+ *****************************************************************************/
 
 typedef enum _PVRSRV_SYNCVAL_MODE_
 {
@@ -698,12 +938,18 @@ IMG_IMPORT PVRSRV_SYNCVAL PVRSRVGetPendingOpSyncVal(PPVRSRV_CLIENT_MEM_INFO psMe
        PVRSRV_SYNCVAL_MODE eMode);
 
 
+/******************************************************************************
+ * Common Device Class Enumeration
+ *****************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVEnumerateDeviceClass(IMG_CONST PVRSRV_CONNECTION *psConnection,
                                                                                                        PVRSRV_DEVICE_CLASS DeviceClass,
                                                                                                        IMG_UINT32 *pui32DevCount,
                                                                                                        IMG_UINT32 *pui32DevID);
 
+/******************************************************************************
+ * Display Device Class API definition
+ *****************************************************************************/
 IMG_IMPORT
 IMG_HANDLE IMG_CALLCONV PVRSRVOpenDCDevice(IMG_CONST PVRSRV_DEV_DATA *psDevData,
                                                                                        IMG_UINT32 ui32DeviceID);
@@ -725,10 +971,11 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVEnumDCDims (IMG_HANDLE hDevice,
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDCSystemBuffer(IMG_HANDLE hDevice,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                               IMG_SID *phBuffer);
+                                                                               IMG_SID *phBuffer
 #else
-                                                                               IMG_HANDLE *phBuffer);
+                                                                               IMG_HANDLE *phBuffer
 #endif
+       );
 
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDCInfo(IMG_HANDLE hDevice,
@@ -743,18 +990,20 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateDCSwapChain (IMG_HANDLE                             hDevice,
                                                                                                        IMG_UINT32                              ui32OEMFlags,
                                                                                                        IMG_UINT32                              *pui32SwapChainID,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                                                       IMG_SID                                 *phSwapChain);
+                                                                                                       IMG_SID                                 *phSwapChain
 #else
-                                                                                                       IMG_HANDLE                              *phSwapChain);
+                                                                                                       IMG_HANDLE                              *phSwapChain
 #endif
+       );
 
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyDCSwapChain (IMG_HANDLE hDevice,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                                       IMG_SID hSwapChain);
+                                                                                       IMG_SID hSwapChain
 #else
-                                                                                       IMG_HANDLE              hSwapChain);
+                                                                                       IMG_HANDLE              hSwapChain
 #endif
+       );
 
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVSetDCDstRect (IMG_HANDLE hDevice,
@@ -796,11 +1045,23 @@ IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDCBuffers(IMG_HANDLE hDevice,
 #if defined (SUPPORT_SID_INTERFACE)
                                                                        IMG_SID     hSwapChain,
-                                                                       IMG_SID    *phBuffer);
+                                                                       IMG_SID    *phBuffer
 #else
                                                                        IMG_HANDLE hSwapChain,
-                                                                       IMG_HANDLE *phBuffer);
+                                                                       IMG_HANDLE *phBuffer
+#endif
+       );
+
+IMG_IMPORT
+PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDCBuffers2(IMG_HANDLE hDevice,
+#if defined (SUPPORT_SID_INTERFACE)
+                                                                                         IMG_SID    hSwapChain,
+                                                                                         IMG_SID   *phBuffer,
+#else
+                                                                                         IMG_HANDLE hSwapChain,
+                                                                                         IMG_HANDLE *phBuffer,
 #endif
+                                                                                         IMG_SYS_PHYADDR *psPhyAddr);
 
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVSwapToDCBuffer (IMG_HANDLE hDevice,
@@ -813,20 +1074,37 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSwapToDCBuffer (IMG_HANDLE hDevice,
                                                                                IMG_RECT  *psClipRect,
                                                                                IMG_UINT32 ui32SwapInterval,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                               IMG_SID hPrivateTag);
+                                                                               IMG_SID hPrivateTag
 #else
-                                                                               IMG_HANDLE hPrivateTag);
+                                                                               IMG_HANDLE hPrivateTag
 #endif
+       );
 
 IMG_IMPORT
-PVRSRV_ERROR IMG_CALLCONV PVRSRVSwapToDCSystem (IMG_HANDLE hDevice,
+PVRSRV_ERROR IMG_CALLCONV PVRSRVSwapToDCBuffer2 (IMG_HANDLE hDevice,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                               IMG_SID hSwapChain);
+                                                                               IMG_SID    hBuffer,
 #else
-                                                                               IMG_HANDLE hSwapChain);
+                                                                               IMG_HANDLE hBuffer,
 #endif
+                                                                               IMG_UINT32 ui32SwapInterval,
+                                                                               PVRSRV_CLIENT_MEM_INFO **ppsMemInfos,
+                                                                               IMG_UINT32 ui32NumMemInfos,
+                                                                               IMG_PVOID  pvPrivData,
+                                                                               IMG_UINT32 ui32PrivDataLength);
 
+IMG_IMPORT
+PVRSRV_ERROR IMG_CALLCONV PVRSRVSwapToDCSystem (IMG_HANDLE hDevice,
+#if defined (SUPPORT_SID_INTERFACE)
+                                                                               IMG_SID hSwapChain
+#else
+                                                                               IMG_HANDLE hSwapChain
+#endif
+       );
 
+/******************************************************************************
+ * Buffer Device Class API definition
+ *****************************************************************************/
 IMG_IMPORT
 IMG_HANDLE IMG_CALLCONV PVRSRVOpenBCDevice(IMG_CONST PVRSRV_DEV_DATA *psDevData,
                                                                                        IMG_UINT32 ui32DeviceID);
@@ -843,12 +1121,16 @@ IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetBCBuffer(IMG_HANDLE hDevice,
                                                                                                IMG_UINT32 ui32BufferIndex,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                                               IMG_SID   *phBuffer);
+                                                                                               IMG_SID   *phBuffer
 #else
-                                                                                               IMG_HANDLE *phBuffer);
+                                                                                               IMG_HANDLE *phBuffer
 #endif
+       );
 
 
+/******************************************************************************
+ * PDUMP Function prototypes...
+ *****************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVPDumpInit(IMG_CONST PVRSRV_CONNECTION *psConnection);
 
@@ -1051,6 +1333,11 @@ IMG_IMPORT IMG_BOOL IMG_CALLCONV PVRSRVGetAppHint(IMG_VOID                       *pvHintState,
                                                                                                  const IMG_VOID        *pvDefault,
                                                                                                  IMG_VOID                      *pvReturn);
 
+/******************************************************************************
+ * Memory API(s)
+ *****************************************************************************/
+
+/* Exported APIs */
 IMG_IMPORT IMG_PVOID IMG_CALLCONV PVRSRVAllocUserModeMem (IMG_SIZE_T ui32Size);
 IMG_IMPORT IMG_PVOID IMG_CALLCONV PVRSRVCallocUserModeMem (IMG_SIZE_T ui32Size);
 IMG_IMPORT IMG_PVOID IMG_CALLCONV PVRSRVReallocUserModeMem (IMG_PVOID pvBase, IMG_SIZE_T uNewSize);
@@ -1061,11 +1348,79 @@ IMG_IMPORT IMG_VOID PVRSRVMemSet(IMG_VOID *pvDest, IMG_UINT8 ui8Value, IMG_SIZE_
 struct _PVRSRV_MUTEX_OPAQUE_STRUCT_;
 typedef        struct  _PVRSRV_MUTEX_OPAQUE_STRUCT_ *PVRSRV_MUTEX_HANDLE;
 
+
+#if defined(PVR_DEBUG_MUTEXES)
+
+IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateMutex(PVRSRV_MUTEX_HANDLE *phMutex,
+                                                                                                          IMG_CHAR pszMutexName[],
+                                                                                                          IMG_CHAR pszFilename[],
+                                                                                                          IMG_INT iLine);
+IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyMutex(PVRSRV_MUTEX_HANDLE hMutex,
+                                                                                                               IMG_CHAR pszMutexName[],
+                                                                                                               IMG_CHAR pszFilename[],
+                                                                                                               IMG_INT iLine);
+IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVLockMutex(PVRSRV_MUTEX_HANDLE hMutex,
+                                                                                                IMG_CHAR pszMutexName[],
+                                                                                                IMG_CHAR pszFilename[],
+                                                                                                IMG_INT iLine);
+IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVUnlockMutex(PVRSRV_MUTEX_HANDLE hMutex,
+                                                                                                  IMG_CHAR pszMutexName[],
+                                                                                                  IMG_CHAR pszFilename[],
+                                                                                                  IMG_INT iLine);
+
+#define PVRSRVCreateMutex(phMutex) PVRSRVCreateMutex(phMutex, #phMutex, __FILE__, __LINE__)
+#define PVRSRVDestroyMutex(hMutex) PVRSRVDestroyMutex(hMutex, #hMutex, __FILE__, __LINE__)
+#define PVRSRVLockMutex(hMutex) PVRSRVLockMutex(hMutex, #hMutex, __FILE__, __LINE__)
+#define PVRSRVUnlockMutex(hMutex) PVRSRVUnlockMutex(hMutex, #hMutex, __FILE__, __LINE__)
+
+#else /* defined(PVR_DEBUG_MUTEXES) */
+
 IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateMutex(PVRSRV_MUTEX_HANDLE *phMutex);
 IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyMutex(PVRSRV_MUTEX_HANDLE hMutex);
 IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVLockMutex(PVRSRV_MUTEX_HANDLE hMutex);
 IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVUnlockMutex(PVRSRV_MUTEX_HANDLE hMutex);
 
+#endif /* defined(PVR_DEBUG_MUTEXES) */
+
+
+struct _PVRSRV_RECMUTEX_OPAQUE_STRUCT_;
+typedef        struct  _PVRSRV_RECMUTEX_OPAQUE_STRUCT_ *PVRSRV_RECMUTEX_HANDLE;
+
+
+#if defined(PVR_DEBUG_MUTEXES)
+
+IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateRecursiveMutex(PVRSRV_RECMUTEX_HANDLE *phMutex,
+                                                                                                          IMG_CHAR pszMutexName[],
+                                                                                                          IMG_CHAR pszFilename[],
+                                                                                                          IMG_INT iLine);
+IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyRecursiveMutex(PVRSRV_RECMUTEX_HANDLE hMutex,
+                                                                                                               IMG_CHAR pszMutexName[],
+                                                                                                               IMG_CHAR pszFilename[],
+                                                                                                               IMG_INT iLine);
+IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVLockRecursiveMutex(PVRSRV_RECMUTEX_HANDLE hMutex,
+                                                                                                IMG_CHAR pszMutexName[],
+                                                                                                IMG_CHAR pszFilename[],
+                                                                                                IMG_INT iLine);
+IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVUnlockRecursiveMutex(PVRSRV_RECMUTEX_HANDLE hMutex,
+                                                                                                  IMG_CHAR pszMutexName[],
+                                                                                                  IMG_CHAR pszFilename[],
+                                                                                                  IMG_INT iLine);
+
+#define PVRSRVCreateRecursiveMutex(phMutex) PVRSRVCreateRecursiveMutex(phMutex, #phMutex, __FILE__, __LINE__)
+#define PVRSRVDestroyRecursiveMutex(hMutex) PVRSRVDestroyRecursiveMutex(hMutex, #hMutex, __FILE__, __LINE__)
+#define PVRSRVLockRecursiveMutex(hMutex) PVRSRVLockRecursiveMutex(hMutex, #hMutex, __FILE__, __LINE__)
+#define PVRSRVUnlockRecursiveMutex(hMutex) PVRSRVUnlockRecursiveMutex(hMutex, #hMutex, __FILE__, __LINE__)
+
+#else /* defined(PVR_DEBUG_MUTEXES) */
+
+IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateRecursiveMutex(PVRSRV_RECMUTEX_HANDLE *phMutex);
+IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyRecursiveMutex(PVRSRV_RECMUTEX_HANDLE hMutex);
+IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVLockRecursiveMutex(PVRSRV_RECMUTEX_HANDLE hMutex);
+IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVUnlockRecursiveMutex(PVRSRV_RECMUTEX_HANDLE hMutex);
+
+#endif /* defined(PVR_DEBUG_MUTEXES) */
+
+/* Non-recursive coarse-grained mutex shared between all threads in a proccess */
 IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVLockProcessGlobalMutex(void);
 IMG_IMPORT IMG_VOID IMG_CALLCONV PVRSRVUnlockProcessGlobalMutex(void);
 
@@ -1117,10 +1472,11 @@ static INLINE IMG_VOID PVRSRVPostSemaphore(PVRSRV_SEMAPHORE_HANDLE hSemaphore, I
        PVR_UNREFERENCED_PARAMETER(iPostCount);
 }
 
-#endif 
+#endif /* !defined(USE_CODE) */
 
 
-#if (defined(DEBUG) && (defined(__linux__) || defined(__QNXNTO__)))
+/* Non-exported APIs */
+#if defined(DEBUG) && (defined(__linux__) || defined(__QNXNTO__) )
 IMG_IMPORT IMG_PVOID IMG_CALLCONV PVRSRVAllocUserModeMemTracking(IMG_SIZE_T ui32Size, IMG_CHAR *pszFileName, IMG_UINT32 ui32LineNumber);
 
 IMG_IMPORT IMG_PVOID IMG_CALLCONV PVRSRVCallocUserModeMemTracking(IMG_SIZE_T ui32Size, IMG_CHAR *pszFileName, IMG_UINT32 ui32LineNumber);
@@ -1129,33 +1485,84 @@ IMG_IMPORT IMG_VOID  IMG_CALLCONV PVRSRVFreeUserModeMemTracking(IMG_VOID *pvMem)
 
 IMG_IMPORT IMG_PVOID IMG_CALLCONV PVRSRVReallocUserModeMemTracking(IMG_VOID *pvMem, IMG_SIZE_T ui32NewSize, 
                                                                                                          IMG_CHAR *pszFileName, IMG_UINT32 ui32LineNumber);
-#endif 
+#endif /* defined(DEBUG) && (defined(__linux__) || defined(_UITRON_)) */
+
+/******************************************************************************
+ * PVR Event Object API(s)
+ *****************************************************************************/
 
 IMG_IMPORT PVRSRV_ERROR PVRSRVEventObjectWait(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                       IMG_EVENTSID hOSEvent);
+                                                                       IMG_EVENTSID hOSEvent
 #else
-                                                                       IMG_HANDLE hOSEvent);
+                                                                       IMG_HANDLE hOSEvent
 #endif
+       );
 
+/*!
+ ******************************************************************************
+
+ @Function             PVRSRVCreateSyncInfoModObj
+
+ @Description  Creates an empty Modification object to be later used by PVRSRVModifyPendingSyncOps
+
+ ******************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateSyncInfoModObj(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                                                        IMG_SID *phKernelSyncInfoModObj);
+                                                                                                        IMG_SID *phKernelSyncInfoModObj
 #else
-                                                                                                        IMG_HANDLE *phKernelSyncInfoModObj);
+                                                                                                        IMG_HANDLE *phKernelSyncInfoModObj
 #endif
+       );
+
+/*!
+ ******************************************************************************
 
+ @Function             PVRSRVDestroySyncInfoModObj
+
+ @Description  Destroys a Modification object.  Must be empty.
+
+ ******************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroySyncInfoModObj(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                                                         IMG_SID hKernelSyncInfoModObj);
+                                                                                                         IMG_SID hKernelSyncInfoModObj
 #else
-                                                                                                         IMG_HANDLE hKernelSyncInfoModObj);
+                                                                                                         IMG_HANDLE hKernelSyncInfoModObj
 #endif
+       );
+
 
 
+/*!
+ ******************************************************************************
 
+ @Function             PVRSRVModifyPendingSyncOps
+
+ @Description  Returns PRE-INCREMENTED sync op values. Performs thread safe increment
+                               of sync ops values as specified by ui32ModifyFlags.
+
+                               PVRSRV_ERROR_RETRY is returned if the supplied modification object
+                is not empty.  This is on the assumption that a different thread
+                               will imminently call PVRSRVModifyCompleteSyncOps.  This thread should
+                               sleep before retrying.  It should be regarded as an error if no such
+                               other thread exists.
+
+                               Note that this API has implied locking semantics, as follows:
+
+                               PVRSRVModifyPendingSyncOps() 
+                                       -  announces an operation on the buffer is "pending", and 
+                                                  conceptually takes a ticket to represent your place in the queue.
+                                               -  NB: ** exclusive access to the resource is  _NOT_ granted at this time **
+                               PVRSRVSyncOpsFlushToModObj()
+                                       -  ensures you have exclusive access to the resource (conceptually, a LOCK)
+                                               -  the previously "pending" operation can now be regarded as "in progress"
+                               PVRSRVModifyCompleteSyncOps()
+                                       -  declares that the previously "in progress" operation is now complete. (UNLOCK)
+                               
+
+ ******************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVModifyPendingSyncOps(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -1168,14 +1575,49 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVModifyPendingSyncOps(const PVRSRV_CONNECTION *ps
                                                                                                          IMG_UINT32 *pui32ReadOpsPending,
                                                                                                          IMG_UINT32 *pui32WriteOpsPending);
 
+/*!
+ ******************************************************************************
+
+ @Function             PVRSRVModifyCompleteSyncOps
+
+ @Description  Performs thread safe increment of sync ops values as specified
+                by the ui32ModifyFlags that were given to PVRSRVModifyPendingSyncOps.
+                               The supplied Modification Object will become empty.
+
+                               Note that this API has implied locking semantics, as
+                               described above in PVRSRVModifyPendingSyncOps
+
+ ******************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVModifyCompleteSyncOps(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
-                                                                                                         IMG_SID hKernelSyncInfoModObj);
+                                                                                                         IMG_SID hKernelSyncInfoModObj
 #else
-                                                                                                         IMG_HANDLE hKernelSyncInfoModObj);
+                                                                                                         IMG_HANDLE hKernelSyncInfoModObj
 #endif
+       );
+
+/*!
+ ******************************************************************************
+
+ @Function     PVRSRVSyncOpsTakeToken
+
+ @Description Takes a "deli-counter" style token for future use with
+              PVRSRVSyncOpsFlushToToken().  In practice this means
+              recording a snapshot of the current "pending" values.  A
+              future PVRSRVSyncOpsFlushToToken() will ensure that all
+              operations that were pending at the time of this
+              PVRSRVSyncOpsTakeToken() call will be flushed.
+              Operations may be subsequently queued after this call
+              and would not be flushed.  The caller is required to
+              provide storage for the token.  The token is disposable
+              - i.e. the caller can simply let the token go out of
+              scope without telling us... in particular, there is no
+              obligation to call PVRSRVSyncOpsFlushToToken().
+              Multiple tokens may be taken.  There is no implied
+              locking with this API.
 
+ ******************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVSyncOpsTakeToken(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -1184,6 +1626,22 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSyncOpsTakeToken(const PVRSRV_CONNECTION *psConn
                                                                                                 const PVRSRV_CLIENT_SYNC_INFO *psSyncInfo,
 #endif
                                                                                                 PVRSRV_SYNC_TOKEN *psSyncToken);
+/*!
+ ******************************************************************************
+
+ @Function     PVRSRVSyncOpsFlushToToken
+
+ @Description Tests whether the dependencies for a pending sync op modification
+              have been satisfied.  If this function returns PVRSRV_OK, then the
+              "complete" counts have caught up with the snapshot of the "pending"
+              values taken when PVRSRVSyncOpsTakeToken() was called.
+              In the event that the dependencies are not (yet) met,
+                         this call will auto-retry if bWait is specified, otherwise, it will
+                         return PVRSRV_ERROR_RETRY.  (Not really an "error")
+
+                         (auto-retry behaviour not implemented)
+
+ ******************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVSyncOpsFlushToToken(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -1193,6 +1651,24 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSyncOpsFlushToToken(const PVRSRV_CONNECTION *psC
 #endif
                                                                                                        const PVRSRV_SYNC_TOKEN *psSyncToken,
                                                                                                        IMG_BOOL bWait);
+/*!
+ ******************************************************************************
+
+ @Function     PVRSRVSyncOpsFlushToModObj
+
+ @Description Tests whether the dependencies for a pending sync op modification
+              have been satisfied.  If this function returns PVRSRV_OK, then the
+              "complete" counts have caught up with the snapshot of the "pending"
+              values taken when PVRSRVModifyPendingSyncOps() was called.
+              PVRSRVModifyCompleteSyncOps() can then be called without risk of
+                         stalling.  In the event that the dependencies are not (yet) met,
+                         this call will auto-retry if bWait is specified, otherwise, it will
+                         return PVRSRV_ERROR_RETRY.  (Not really an "error")
+
+                         Note that this API has implied locking semantics, as
+                         described above in PVRSRVModifyPendingSyncOps
+
+ ******************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVSyncOpsFlushToModObj(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -1202,33 +1678,94 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSyncOpsFlushToModObj(const PVRSRV_CONNECTION *ps
 #endif
                                                                                                         IMG_BOOL bWait);
 
+/*!
+ ******************************************************************************
+
+ @Function     PVRSRVSyncOpsFlushToDelta
+
+ @Description Compares the number of outstanding operations (pending count minus
+              complete count) with the limit specified.  If no more than ui32Delta
+              operations are outstanding, this function returns PVRSRV_OK.
+              In the event that there are too many outstanding operations,
+                         this call will auto-retry if bWait is specified, otherwise, it will
+                         return PVRSRV_ERROR_RETRY.  (Not really an "error")
+
+ ******************************************************************************/
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVSyncOpsFlushToDelta(const PVRSRV_CONNECTION *psConnection,
                                                                                                        PVRSRV_CLIENT_SYNC_INFO *psClientSyncInfo,
                                                                                                        IMG_UINT32 ui32Delta,
                                                                                                        IMG_BOOL bWait);
 
+/*!
+ ******************************************************************************
+
+ @Function     PVRSRVAllocSyncInfo
+
+ @Description Creates a Sync Object.  Unlike the sync objects created
+                         automatically with "PVRSRVAllocDeviceMem", the sync objects
+                         returned by this function do _not_ have a UM mapping to the
+                         sync data and they do _not_ have the device virtual address
+                         of the "opscomplete" fields.  These data are to be deprecated.
+
+ ******************************************************************************/
+
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocSyncInfo(IMG_CONST PVRSRV_DEV_DATA        *psDevData,
                                                                                          PVRSRV_CLIENT_SYNC_INFO **ppsSyncInfo);
 
+/*!
+ ******************************************************************************
+
+ @Function     PVRSRVFreeSyncInfo
+
+ @Description Destroys a Sync Object created via
+              PVRSRVAllocSyncInfo.
+
+ ******************************************************************************/
+
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVFreeSyncInfo(IMG_CONST PVRSRV_DEV_DATA *psDevData,
                                                                                         PVRSRV_CLIENT_SYNC_INFO *psSyncInfo);
 
+/*!
+ ******************************************************************************
+
+ @Function             PVRSRVGetErrorString
+
+ @Description  Returns a text string relating to the PVRSRV_ERROR enum.
+
+ ******************************************************************************/
 IMG_IMPORT
 const IMG_CHAR *PVRSRVGetErrorString(PVRSRV_ERROR eError);
 
 
+/*!
+ ******************************************************************************
+
+ @Function             PVRSRVCacheInvalidate
+
+ @Description   Invalidate the CPU cache for a specified memory
+                area. Note that PVRSRVGetMiscInfo provides similar cpu
+                cache flush/invalidate functionality for some platforms.
+
+ ******************************************************************************/
+
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVCacheInvalidate(const PVRSRV_CONNECTION *psConnection,
                                                 IMG_PVOID pvLinearAddress,
                                                    IMG_UINT32 ui32Size);
 
+/******************************************************************************
+ Time wrapping macro
+******************************************************************************/
 #define TIME_NOT_PASSED_UINT32(a,b,c)          (((a) - (b)) < (c))
 
 #if defined (__cplusplus)
 }
 #endif
-#endif 
+#endif /* __SERVICES_H__ */
 
+/******************************************************************************
+ End of file (services.h)
+******************************************************************************/
index 54dd4d9..80df117 100644 (file)
@@ -1,34 +1,62 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Services definitions required by external drivers
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provides services data structures, defines and prototypes
+                required by external drivers.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined (__SERVICESEXT_H__)
 #define __SERVICESEXT_H__
 
-#define PVRSRV_LOCKFLG_READONLY        (1)             
+/*
+ * Lock buffer read/write flags
+ */
+#define PVRSRV_LOCKFLG_READONLY        (1)             /*!< The locking process will only read the locked surface */
 
+/*!
+ *****************************************************************************
+ * Error values
+ *
+ * NOTE: If you change this, make sure you update the error texts in
+ *   services4/include/pvrsrv_errors.h to match.
+ *
+ *****************************************************************************/
 typedef enum _PVRSRV_ERROR_
 {
        PVRSRV_OK = 0,
@@ -267,6 +295,10 @@ typedef enum _PVRSRV_ERROR_
 } PVRSRV_ERROR;
 
 
+/*!
+ *****************************************************************************
+ * List of known device classes.
+ *****************************************************************************/
 typedef enum _PVRSRV_DEVICE_CLASS_
 {
        PVRSRV_DEVICE_CLASS_3D                          = 0 ,
@@ -279,14 +311,18 @@ typedef enum _PVRSRV_DEVICE_CLASS_
 } PVRSRV_DEVICE_CLASS;
 
 
+/*!
+ *****************************************************************************
+ *     States for power management
+ *****************************************************************************/
 typedef enum _PVRSRV_SYS_POWER_STATE_
 {
-       PVRSRV_SYS_POWER_STATE_Unspecified              = -1,   
-       PVRSRV_SYS_POWER_STATE_D0                               = 0,    
-       PVRSRV_SYS_POWER_STATE_D1                               = 1,    
-       PVRSRV_SYS_POWER_STATE_D2                               = 2,    
-       PVRSRV_SYS_POWER_STATE_D3                               = 3,    
-       PVRSRV_SYS_POWER_STATE_D4                               = 4,    
+       PVRSRV_SYS_POWER_STATE_Unspecified              = -1,   /*!< Unspecified : Uninitialised */
+       PVRSRV_SYS_POWER_STATE_D0                               = 0,    /*!< On */
+       PVRSRV_SYS_POWER_STATE_D1                               = 1,    /*!< User Idle */
+       PVRSRV_SYS_POWER_STATE_D2                               = 2,    /*!< System Idle / sleep */
+       PVRSRV_SYS_POWER_STATE_D3                               = 3,    /*!< Suspend / Hibernate */
+       PVRSRV_SYS_POWER_STATE_D4                               = 4,    /*!< shutdown */
 
        PVRSRV_SYS_POWER_STATE_FORCE_I32 = 0x7fffffff
 
@@ -295,16 +331,17 @@ typedef enum _PVRSRV_SYS_POWER_STATE_
 
 typedef enum _PVRSRV_DEV_POWER_STATE_
 {
-       PVRSRV_DEV_POWER_STATE_DEFAULT  = -1,   
-       PVRSRV_DEV_POWER_STATE_ON               = 0,    
-       PVRSRV_DEV_POWER_STATE_IDLE             = 1,    
-       PVRSRV_DEV_POWER_STATE_OFF              = 2,    
+       PVRSRV_DEV_POWER_STATE_DEFAULT  = -1,   /*!< Default state for the device */
+       PVRSRV_DEV_POWER_STATE_ON               = 0,    /*!< Running */
+       PVRSRV_DEV_POWER_STATE_IDLE             = 1,    /*!< Powered but operation paused */
+       PVRSRV_DEV_POWER_STATE_OFF              = 2,    /*!< Unpowered */
 
        PVRSRV_DEV_POWER_STATE_FORCE_I32 = 0x7fffffff
 
-} PVRSRV_DEV_POWER_STATE, *PPVRSRV_DEV_POWER_STATE;    
+} PVRSRV_DEV_POWER_STATE, *PPVRSRV_DEV_POWER_STATE;    /* PRQA S 3205 */
 
 
+/* Power transition handler prototypes */
 typedef PVRSRV_ERROR (*PFN_PRE_POWER) (IMG_HANDLE                              hDevHandle,
                                                                           PVRSRV_DEV_POWER_STATE       eNewPowerState,
                                                                           PVRSRV_DEV_POWER_STATE       eCurrentPowerState);
@@ -312,6 +349,7 @@ typedef PVRSRV_ERROR (*PFN_POST_POWER) (IMG_HANDLE                          hDevHandle,
                                                                                PVRSRV_DEV_POWER_STATE  eNewPowerState,
                                                                                PVRSRV_DEV_POWER_STATE  eCurrentPowerState);
 
+/* Clock speed handler prototypes */
 typedef PVRSRV_ERROR (*PFN_PRE_CLOCKSPEED_CHANGE) (IMG_HANDLE                          hDevHandle,
                                                                                                   IMG_BOOL                                     bIdleDevice,
                                                                                                   PVRSRV_DEV_POWER_STATE       eCurrentPowerState);
@@ -320,13 +358,23 @@ typedef PVRSRV_ERROR (*PFN_POST_CLOCKSPEED_CHANGE) (IMG_HANDLE                            hDevHandle,
                                                                                                        PVRSRV_DEV_POWER_STATE  eCurrentPowerState);
 
 
+/*****************************************************************************
+ * Enumeration of all possible pixel types. Where applicable, Ordering of name
+ * is in reverse order of memory bytes (i.e. as a word in little endian).
+ * e.g. A8R8G8B8 is in memory as 4 bytes in order: BB GG RR AA
+ *
+ * NOTE: When modifying this structure please update the client driver format
+ *       tables located in %WORKROOT%/eurasia/codegen/pixfmts using the tool
+ *       located in %WORKROOT%/eurasia/tools/intern/TextureFormatParser.
+ *
+ *****************************************************************************/
 typedef enum _PVRSRV_PIXEL_FORMAT_ {
-       
+       /* Basic types */
        PVRSRV_PIXEL_FORMAT_UNKNOWN                             =  0,
        PVRSRV_PIXEL_FORMAT_RGB565                              =  1,
        PVRSRV_PIXEL_FORMAT_RGB555                              =  2,
-       PVRSRV_PIXEL_FORMAT_RGB888                              =  3,   
-       PVRSRV_PIXEL_FORMAT_BGR888                              =  4,   
+       PVRSRV_PIXEL_FORMAT_RGB888                              =  3,   /*!< 24bit */
+       PVRSRV_PIXEL_FORMAT_BGR888                              =  4,   /*!< 24bit */
        PVRSRV_PIXEL_FORMAT_GREY_SCALE                  =  8,
        PVRSRV_PIXEL_FORMAT_PAL12                               = 13,
        PVRSRV_PIXEL_FORMAT_PAL8                                = 14,
@@ -345,8 +393,8 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_BGRA8888                    = 28,
        PVRSRV_PIXEL_FORMAT_XRGB4444                    = 29,
        PVRSRV_PIXEL_FORMAT_ARGB8332                    = 30,
-       PVRSRV_PIXEL_FORMAT_A2RGB10                             = 31,   
-       PVRSRV_PIXEL_FORMAT_A2BGR10                             = 32,   
+       PVRSRV_PIXEL_FORMAT_A2RGB10                             = 31,   /*!< 32bpp, 10 bits for R, G, B, 2 bits for A */
+       PVRSRV_PIXEL_FORMAT_A2BGR10                             = 32,   /*!< 32bpp, 10 bits for B, G, R, 2 bits for A */
        PVRSRV_PIXEL_FORMAT_P8                                  = 33,
        PVRSRV_PIXEL_FORMAT_L8                                  = 34,
        PVRSRV_PIXEL_FORMAT_A8L8                                = 35,
@@ -362,7 +410,7 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_D24S8                               = 45,
        PVRSRV_PIXEL_FORMAT_D24X8                               = 46,
 
-       
+       /* Added to ensure TQ build */
        PVRSRV_PIXEL_FORMAT_ABGR16                              = 47,
        PVRSRV_PIXEL_FORMAT_ABGR16F                             = 48,
        PVRSRV_PIXEL_FORMAT_ABGR32                              = 49,
@@ -373,22 +421,22 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_GR32                                = 54,
        PVRSRV_PIXEL_FORMAT_E5BGR9                              = 55,
 
-       
+       /* reserved types */
        PVRSRV_PIXEL_FORMAT_RESERVED1                   = 56,
        PVRSRV_PIXEL_FORMAT_RESERVED2                   = 57,
        PVRSRV_PIXEL_FORMAT_RESERVED3                   = 58,
        PVRSRV_PIXEL_FORMAT_RESERVED4                   = 59,
        PVRSRV_PIXEL_FORMAT_RESERVED5                   = 60,
 
-       
+       /* RGB space packed formats */
        PVRSRV_PIXEL_FORMAT_R8G8_B8G8                   = 61,
        PVRSRV_PIXEL_FORMAT_G8R8_G8B8                   = 62,
 
-       
+       /* YUV space planar formats */
        PVRSRV_PIXEL_FORMAT_NV11                                = 63,
        PVRSRV_PIXEL_FORMAT_NV12                                = 64,
 
-       
+       /* YUV space packed formats */
        PVRSRV_PIXEL_FORMAT_YUY2                                = 65,
        PVRSRV_PIXEL_FORMAT_YUV420                              = 66,
        PVRSRV_PIXEL_FORMAT_YUV444                              = 67,
@@ -398,107 +446,107 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_UYVY                                = 71,
        PVRSRV_PIXEL_FORMAT_VYUY                                = 72,
 
-       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_UYVY             = 73,   
-       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_YUYV             = 74,   
-       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_YVYU             = 75,   
-       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_VYUY             = 76,   
-       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_AYUV             = 77,   
-
-       
-       PVRSRV_PIXEL_FORMAT_A32B32G32R32                = 78,   
-       PVRSRV_PIXEL_FORMAT_A32B32G32R32F               = 79,   
-       PVRSRV_PIXEL_FORMAT_A32B32G32R32_UINT   = 80,   
-       PVRSRV_PIXEL_FORMAT_A32B32G32R32_SINT   = 81,   
-
-       
-       PVRSRV_PIXEL_FORMAT_B32G32R32                   = 82,   
-       PVRSRV_PIXEL_FORMAT_B32G32R32F                  = 83,   
-       PVRSRV_PIXEL_FORMAT_B32G32R32_UINT              = 84,   
-       PVRSRV_PIXEL_FORMAT_B32G32R32_SINT              = 85,   
-
-       
-       PVRSRV_PIXEL_FORMAT_G32R32                              = 86,   
-       PVRSRV_PIXEL_FORMAT_G32R32F                             = 87,   
-       PVRSRV_PIXEL_FORMAT_G32R32_UINT                 = 88,   
-       PVRSRV_PIXEL_FORMAT_G32R32_SINT                 = 89,   
-
-       
-       PVRSRV_PIXEL_FORMAT_D32F                                = 90,   
-       PVRSRV_PIXEL_FORMAT_R32                                 = 91,   
-       PVRSRV_PIXEL_FORMAT_R32F                                = 92,   
-       PVRSRV_PIXEL_FORMAT_R32_UINT                    = 93,   
-       PVRSRV_PIXEL_FORMAT_R32_SINT                    = 94,   
-
-       
-       PVRSRV_PIXEL_FORMAT_A16B16G16R16                = 95,   
-       PVRSRV_PIXEL_FORMAT_A16B16G16R16F               = 96,   
-       PVRSRV_PIXEL_FORMAT_A16B16G16R16_SINT   = 97,   
-       PVRSRV_PIXEL_FORMAT_A16B16G16R16_SNORM  = 98,   
-       PVRSRV_PIXEL_FORMAT_A16B16G16R16_UINT   = 99,   
-       PVRSRV_PIXEL_FORMAT_A16B16G16R16_UNORM  = 100,  
-
-       
-       PVRSRV_PIXEL_FORMAT_G16R16                              = 101,  
-       PVRSRV_PIXEL_FORMAT_G16R16F                             = 102,  
-       PVRSRV_PIXEL_FORMAT_G16R16_UINT                 = 103,  
-       PVRSRV_PIXEL_FORMAT_G16R16_UNORM                = 104,  
-       PVRSRV_PIXEL_FORMAT_G16R16_SINT                 = 105,  
-       PVRSRV_PIXEL_FORMAT_G16R16_SNORM                = 106,  
-
-       
-       PVRSRV_PIXEL_FORMAT_R16                                 = 107,  
-       PVRSRV_PIXEL_FORMAT_R16F                                = 108,  
-       PVRSRV_PIXEL_FORMAT_R16_UINT                    = 109,  
-       PVRSRV_PIXEL_FORMAT_R16_UNORM                   = 110,  
-       PVRSRV_PIXEL_FORMAT_R16_SINT                    = 111,  
-       PVRSRV_PIXEL_FORMAT_R16_SNORM                   = 112,  
-
-       
-       PVRSRV_PIXEL_FORMAT_X8R8G8B8                    = 113,  
-       PVRSRV_PIXEL_FORMAT_X8R8G8B8_UNORM              = 114,  
-       PVRSRV_PIXEL_FORMAT_X8R8G8B8_UNORM_SRGB = 115,  
-
-       PVRSRV_PIXEL_FORMAT_A8R8G8B8                    = 116,  
-       PVRSRV_PIXEL_FORMAT_A8R8G8B8_UNORM              = 117,  
-       PVRSRV_PIXEL_FORMAT_A8R8G8B8_UNORM_SRGB = 118,  
-
-       PVRSRV_PIXEL_FORMAT_A8B8G8R8                    = 119,  
-       PVRSRV_PIXEL_FORMAT_A8B8G8R8_UINT               = 120,  
-       PVRSRV_PIXEL_FORMAT_A8B8G8R8_UNORM              = 121,  
-       PVRSRV_PIXEL_FORMAT_A8B8G8R8_UNORM_SRGB = 122,  
-       PVRSRV_PIXEL_FORMAT_A8B8G8R8_SINT               = 123,  
-       PVRSRV_PIXEL_FORMAT_A8B8G8R8_SNORM              = 124,  
-
-       
-       PVRSRV_PIXEL_FORMAT_G8R8                                = 125,  
-       PVRSRV_PIXEL_FORMAT_G8R8_UINT                   = 126,  
-       PVRSRV_PIXEL_FORMAT_G8R8_UNORM                  = 127,  
-       PVRSRV_PIXEL_FORMAT_G8R8_SINT                   = 128,  
-       PVRSRV_PIXEL_FORMAT_G8R8_SNORM                  = 129,  
-
-       
-       PVRSRV_PIXEL_FORMAT_A8                                  = 130,  
-       PVRSRV_PIXEL_FORMAT_R8                                  = 131,  
-       PVRSRV_PIXEL_FORMAT_R8_UINT                             = 132,  
-       PVRSRV_PIXEL_FORMAT_R8_UNORM                    = 133,  
-       PVRSRV_PIXEL_FORMAT_R8_SINT                             = 134,  
-       PVRSRV_PIXEL_FORMAT_R8_SNORM                    = 135,  
-
-       
-       PVRSRV_PIXEL_FORMAT_A2B10G10R10                 = 136,  
-       PVRSRV_PIXEL_FORMAT_A2B10G10R10_UNORM   = 137,  
-       PVRSRV_PIXEL_FORMAT_A2B10G10R10_UINT    = 138,  
-
-       
-       PVRSRV_PIXEL_FORMAT_B10G11R11                   = 139,  
-       PVRSRV_PIXEL_FORMAT_B10G11R11F                  = 140,  
-
-       
-       PVRSRV_PIXEL_FORMAT_X24G8R32                    = 141,  
-       PVRSRV_PIXEL_FORMAT_G8R24                               = 142,  
+       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_UYVY             = 73,   /*!< See http://www.fourcc.org/yuv.php#UYVY */
+       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_YUYV             = 74,   /*!< See http://www.fourcc.org/yuv.php#YUYV */
+       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_YVYU             = 75,   /*!< See http://www.fourcc.org/yuv.php#YVYU */
+       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_VYUY             = 76,   /*!< No fourcc.org link */
+       PVRSRV_PIXEL_FORMAT_FOURCC_ORG_AYUV             = 77,   /*!< See http://www.fourcc.org/yuv.php#AYUV */
+
+       /* 4 component, 32 bits per component types */
+       PVRSRV_PIXEL_FORMAT_A32B32G32R32                = 78,   /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_A32B32G32R32F               = 79,   /*!< float type */
+       PVRSRV_PIXEL_FORMAT_A32B32G32R32_UINT   = 80,   /*!< uint type */
+       PVRSRV_PIXEL_FORMAT_A32B32G32R32_SINT   = 81,   /*!< sint type */
+
+       /* 3 component, 32 bits per component types */
+       PVRSRV_PIXEL_FORMAT_B32G32R32                   = 82,   /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_B32G32R32F                  = 83,   /*!< float data */
+       PVRSRV_PIXEL_FORMAT_B32G32R32_UINT              = 84,   /*!< uint data */
+       PVRSRV_PIXEL_FORMAT_B32G32R32_SINT              = 85,   /*!< signed int data */
+
+       /* 2 component, 32 bits per component types */
+       PVRSRV_PIXEL_FORMAT_G32R32                              = 86,   /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_G32R32F                             = 87,   /*!< float */
+       PVRSRV_PIXEL_FORMAT_G32R32_UINT                 = 88,   /*!< uint */
+       PVRSRV_PIXEL_FORMAT_G32R32_SINT                 = 89,   /*!< signed int */
+
+       /* 1 component, 32 bits per component types */
+       PVRSRV_PIXEL_FORMAT_D32F                                = 90,   /*!< float depth */
+       PVRSRV_PIXEL_FORMAT_R32                                 = 91,   /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_R32F                                = 92,   /*!< float type */
+       PVRSRV_PIXEL_FORMAT_R32_UINT                    = 93,   /*!< unsigned int type */
+       PVRSRV_PIXEL_FORMAT_R32_SINT                    = 94,   /*!< signed int type */
+
+       /* 4 component, 16 bits per component types */
+       PVRSRV_PIXEL_FORMAT_A16B16G16R16                = 95,   /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_A16B16G16R16F               = 96,   /*!< type float */
+       PVRSRV_PIXEL_FORMAT_A16B16G16R16_SINT   = 97,   /*!< signed ints */
+       PVRSRV_PIXEL_FORMAT_A16B16G16R16_SNORM  = 98,   /*!< signed normalised int */
+       PVRSRV_PIXEL_FORMAT_A16B16G16R16_UINT   = 99,   /*!< unsigned ints */
+       PVRSRV_PIXEL_FORMAT_A16B16G16R16_UNORM  = 100,  /*!< normalised unsigned int */
+
+       /* 2 component, 16 bits per component types */
+       PVRSRV_PIXEL_FORMAT_G16R16                              = 101,  /*!< unspecified type */
+       PVRSRV_PIXEL_FORMAT_G16R16F                             = 102,  /*!< float type */
+       PVRSRV_PIXEL_FORMAT_G16R16_UINT                 = 103,  /*!< unsigned int type */
+       PVRSRV_PIXEL_FORMAT_G16R16_UNORM                = 104,  /*!< unsigned normalised */
+       PVRSRV_PIXEL_FORMAT_G16R16_SINT                 = 105,  /*!< signed int  */
+       PVRSRV_PIXEL_FORMAT_G16R16_SNORM                = 106,  /*!< signed normalised */
+
+       /* 1 component, 16 bits per component types */
+       PVRSRV_PIXEL_FORMAT_R16                                 = 107,  /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_R16F                                = 108,  /*!< float type */
+       PVRSRV_PIXEL_FORMAT_R16_UINT                    = 109,  /*!< unsigned int type */
+       PVRSRV_PIXEL_FORMAT_R16_UNORM                   = 110,  /*!< unsigned normalised int type */
+       PVRSRV_PIXEL_FORMAT_R16_SINT                    = 111,  /*!< signed int type */
+       PVRSRV_PIXEL_FORMAT_R16_SNORM                   = 112,  /*!< signed normalised int type */
+
+       /* 4 component, 8 bits per component types */
+       PVRSRV_PIXEL_FORMAT_X8R8G8B8                    = 113,  /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_X8R8G8B8_UNORM              = 114,  /*!< normalised unsigned int */
+       PVRSRV_PIXEL_FORMAT_X8R8G8B8_UNORM_SRGB = 115,  /*!< normalised uint with sRGB */
+
+       PVRSRV_PIXEL_FORMAT_A8R8G8B8                    = 116,  /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_A8R8G8B8_UNORM              = 117,  /*!< normalised unsigned int */
+       PVRSRV_PIXEL_FORMAT_A8R8G8B8_UNORM_SRGB = 118,  /*!< normalised uint with sRGB */
+
+       PVRSRV_PIXEL_FORMAT_A8B8G8R8                    = 119,  /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_A8B8G8R8_UINT               = 120,  /*!< unsigned int */
+       PVRSRV_PIXEL_FORMAT_A8B8G8R8_UNORM              = 121,  /*!< normalised unsigned int */
+       PVRSRV_PIXEL_FORMAT_A8B8G8R8_UNORM_SRGB = 122,  /*!< normalised unsigned int */
+       PVRSRV_PIXEL_FORMAT_A8B8G8R8_SINT               = 123,  /*!< signed int */
+       PVRSRV_PIXEL_FORMAT_A8B8G8R8_SNORM              = 124,  /*!< normalised signed int */
+
+       /* 2 component, 8 bits per component types */
+       PVRSRV_PIXEL_FORMAT_G8R8                                = 125,  /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_G8R8_UINT                   = 126,  /*!< unsigned int type */
+       PVRSRV_PIXEL_FORMAT_G8R8_UNORM                  = 127,  /*!< unsigned int normalised */
+       PVRSRV_PIXEL_FORMAT_G8R8_SINT                   = 128,  /*!< signed int type */
+       PVRSRV_PIXEL_FORMAT_G8R8_SNORM                  = 129,  /*!< signed int normalised */
+
+       /* 1 component, 8 bits per component types */
+       PVRSRV_PIXEL_FORMAT_A8                                  = 130,  /*!< type unspecified, alpha channel */
+       PVRSRV_PIXEL_FORMAT_R8                                  = 131,  /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_R8_UINT                             = 132,  /*!< unsigned int */
+       PVRSRV_PIXEL_FORMAT_R8_UNORM                    = 133,  /*!< unsigned normalised int */
+       PVRSRV_PIXEL_FORMAT_R8_SINT                             = 134,  /*!< signed int */
+       PVRSRV_PIXEL_FORMAT_R8_SNORM                    = 135,  /*!< signed normalised int */
+
+       /* A2RGB10 types */
+       PVRSRV_PIXEL_FORMAT_A2B10G10R10                 = 136,  /*!< Type unspecified */
+       PVRSRV_PIXEL_FORMAT_A2B10G10R10_UNORM   = 137,  /*!< normalised unsigned int */
+       PVRSRV_PIXEL_FORMAT_A2B10G10R10_UINT    = 138,  /*!< unsigned int */
+
+       /* F11F11F10 types */
+       PVRSRV_PIXEL_FORMAT_B10G11R11                   = 139,  /*!< type unspecified */
+       PVRSRV_PIXEL_FORMAT_B10G11R11F                  = 140,  /*!< float type */
+
+       /* esoteric types */
+       PVRSRV_PIXEL_FORMAT_X24G8R32                    = 141,  /*!< 64 bit, type unspecified (Usually typed to D32S8 style) */
+       PVRSRV_PIXEL_FORMAT_G8R24                               = 142,  /*!< 32 bit, type unspecified (Usually typed to D24S8 style) */
        PVRSRV_PIXEL_FORMAT_X8R24                               = 143,
-       PVRSRV_PIXEL_FORMAT_E5B9G9R9                    = 144,  
-       PVRSRV_PIXEL_FORMAT_R1                                  = 145,  
+       PVRSRV_PIXEL_FORMAT_E5B9G9R9                    = 144,  /*!< 32 bit, shared exponent (RGBE). */
+       PVRSRV_PIXEL_FORMAT_R1                                  = 145,  /*!< 1 bit monochrome */
 
        PVRSRV_PIXEL_FORMAT_RESERVED6                   = 146,
        PVRSRV_PIXEL_FORMAT_RESERVED7                   = 147,
@@ -516,20 +564,20 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_RESERVED19                  = 159,
        PVRSRV_PIXEL_FORMAT_RESERVED20                  = 160,
 
-       
-       PVRSRV_PIXEL_FORMAT_UBYTE4                              = 161,  
-       PVRSRV_PIXEL_FORMAT_SHORT4                              = 162,  
-       PVRSRV_PIXEL_FORMAT_SHORT4N                             = 163,  
-       PVRSRV_PIXEL_FORMAT_USHORT4N                    = 164,  
-       PVRSRV_PIXEL_FORMAT_SHORT2N                             = 165,  
-       PVRSRV_PIXEL_FORMAT_SHORT2                              = 166,  
-       PVRSRV_PIXEL_FORMAT_USHORT2N                    = 167,  
-       PVRSRV_PIXEL_FORMAT_UDEC3                               = 168,  
-       PVRSRV_PIXEL_FORMAT_DEC3N                               = 169,  
-       PVRSRV_PIXEL_FORMAT_F16_2                               = 170,  
-       PVRSRV_PIXEL_FORMAT_F16_4                               = 171,  
-
-       
+       /* DXLegacy vertex types */
+       PVRSRV_PIXEL_FORMAT_UBYTE4                              = 161,  /*!< 4 channels, 1 byte per channel, normalised */
+       PVRSRV_PIXEL_FORMAT_SHORT4                              = 162,  /*!< 4 signed channels, 16 bits each, unnormalised */
+       PVRSRV_PIXEL_FORMAT_SHORT4N                             = 163,  /*!< 4 signed channels, 16 bits each, normalised */
+       PVRSRV_PIXEL_FORMAT_USHORT4N                    = 164,  /*!< 4 unsigned channels, 16 bits each, normalised */
+       PVRSRV_PIXEL_FORMAT_SHORT2N                             = 165,  /*!< 2 signed channels, 16 bits each, normalised */
+       PVRSRV_PIXEL_FORMAT_SHORT2                              = 166,  /*!< 2 signed channels, 16 bits each, unnormalised */
+       PVRSRV_PIXEL_FORMAT_USHORT2N                    = 167,  /*!< 2 unsigned channels, 16 bits each, normalised */
+       PVRSRV_PIXEL_FORMAT_UDEC3                               = 168,  /*!< 3 10-bit channels, unnormalised, unsigned*/
+       PVRSRV_PIXEL_FORMAT_DEC3N                               = 169,  /*!< 3 10-bit channels, signed normalised */
+       PVRSRV_PIXEL_FORMAT_F16_2                               = 170,  /*!< 2 F16 channels */
+       PVRSRV_PIXEL_FORMAT_F16_4                               = 171,  /*!< 4 F16 channels */
+
+       /* misc float types */
        PVRSRV_PIXEL_FORMAT_L_F16                               = 172,
        PVRSRV_PIXEL_FORMAT_L_F16_REP                   = 173,
        PVRSRV_PIXEL_FORMAT_L_F16_A_F16                 = 174,
@@ -540,7 +588,7 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_A_F32                               = 178,
        PVRSRV_PIXEL_FORMAT_L_F32_A_F32                 = 179,
 
-       
+       /* powervr types */
        PVRSRV_PIXEL_FORMAT_PVRTC2                              = 180,
        PVRSRV_PIXEL_FORMAT_PVRTC4                              = 181,
        PVRSRV_PIXEL_FORMAT_PVRTCII2                    = 182,
@@ -557,7 +605,7 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_MONO8                               = 193,
        PVRSRV_PIXEL_FORMAT_MONO16                              = 194,
 
-       
+       /* additional YUV types */
        PVRSRV_PIXEL_FORMAT_C0_YUYV                             = 195,
        PVRSRV_PIXEL_FORMAT_C0_UYVY                             = 196,
        PVRSRV_PIXEL_FORMAT_C0_YVYU                             = 197,
@@ -567,7 +615,7 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_C1_YVYU                             = 201,
        PVRSRV_PIXEL_FORMAT_C1_VYUY                             = 202,
 
-       
+       /* planar YUV types */
        PVRSRV_PIXEL_FORMAT_C0_YUV420_2P_UV             = 203,
        PVRSRV_PIXEL_FORMAT_C0_YUV420_2P_VU             = 204,
        PVRSRV_PIXEL_FORMAT_C0_YUV420_3P                = 205,
@@ -583,7 +631,7 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
        PVRSRV_PIXEL_FORMAT_ABGR1555                    = 213,
        PVRSRV_PIXEL_FORMAT_BGR565                              = 214,                  
 
-       
+       /* 4k aligned planar YUV */
        PVRSRV_PIXEL_FORMAT_C0_4KYUV420_2P_UV   = 215,
        PVRSRV_PIXEL_FORMAT_C0_4KYUV420_2P_VU   = 216,
        PVRSRV_PIXEL_FORMAT_C1_4KYUV420_2P_UV   = 217,
@@ -601,6 +649,10 @@ typedef enum _PVRSRV_PIXEL_FORMAT_ {
 
 } PVRSRV_PIXEL_FORMAT;
 
+/*!
+ *****************************************************************************
+ * Enumeration of possible alpha types.
+ *****************************************************************************/
 typedef enum _PVRSRV_ALPHA_FORMAT_ {
        PVRSRV_ALPHA_FORMAT_UNKNOWN             =  0x00000000,
        PVRSRV_ALPHA_FORMAT_PRE                 =  0x00000001,
@@ -608,6 +660,10 @@ typedef enum _PVRSRV_ALPHA_FORMAT_ {
        PVRSRV_ALPHA_FORMAT_MASK                =  0x0000000F,
 } PVRSRV_ALPHA_FORMAT;
 
+/*!
+ *****************************************************************************
+ * Enumeration of possible alpha types.
+ *****************************************************************************/
 typedef enum _PVRSRV_COLOURSPACE_FORMAT_ {
        PVRSRV_COLOURSPACE_FORMAT_UNKNOWN               =  0x00000000,
        PVRSRV_COLOURSPACE_FORMAT_LINEAR                =  0x00010000,
@@ -616,6 +672,10 @@ typedef enum _PVRSRV_COLOURSPACE_FORMAT_ {
 } PVRSRV_COLOURSPACE_FORMAT;
 
 
+/*
+ * Drawable orientation (in degrees clockwise).
+ * Opposite sense from WSEGL.
+ */
 typedef enum _PVRSRV_ROTATION_ {
        PVRSRV_ROTATE_0         =       0,
        PVRSRV_ROTATE_90        =       1,
@@ -625,55 +685,83 @@ typedef enum _PVRSRV_ROTATION_ {
 
 } PVRSRV_ROTATION;
 
+/*!
+ * Flags for DisplayClassCreateSwapChain.
+ */
 #define PVRSRV_CREATE_SWAPCHAIN_SHARED         (1<<0)
 #define PVRSRV_CREATE_SWAPCHAIN_QUERY          (1<<1)
 #define PVRSRV_CREATE_SWAPCHAIN_OEMOVERLAY     (1<<2)
 
+/*!
+ *****************************************************************************
+ * Structure providing implementation details for serialisation and
+ * synchronisation of operations. This is the fundamental unit on which operations
+ * are synced, and would typically be included in any data structures that require
+ * serialised accesses etc. e.g. MEM_INFO structures
+ *
+ *****************************************************************************/
+/*
+       Sync Data to be shared/mapped between user/kernel
+*/
 typedef struct _PVRSRV_SYNC_DATA_
 {
-       
+       /* CPU accessible WriteOp Info */
        IMG_UINT32                                      ui32WriteOpsPending;
        volatile IMG_UINT32                     ui32WriteOpsComplete;
 
-       
+       /* CPU accessible ReadOp Info */
        IMG_UINT32                                      ui32ReadOpsPending;
        volatile IMG_UINT32                     ui32ReadOpsComplete;
 
-       
+       /* CPU accessible ReadOp2 Info */
+       IMG_UINT32                                      ui32ReadOps2Pending;
+       volatile IMG_UINT32                     ui32ReadOps2Complete;
+
+       /* pdump specific value */
        IMG_UINT32                                      ui32LastOpDumpVal;
        IMG_UINT32                                      ui32LastReadOpDumpVal;
 
+       /* Last write oprtation on this sync */
+       IMG_UINT64                                      ui64LastWrite;
+
 } PVRSRV_SYNC_DATA;
 
+/*
+       Client Sync Info structure
+*/
 typedef struct _PVRSRV_CLIENT_SYNC_INFO_
 {
-       
+       /* mapping of the kernel sync data */
        PVRSRV_SYNC_DATA                *psSyncData;
 
-       
-
-
-       
+       /* Device accessible WriteOp Info */
        IMG_DEV_VIRTADDR                sWriteOpsCompleteDevVAddr;
 
-       
+       /* Device accessible ReadOp Info */
        IMG_DEV_VIRTADDR                sReadOpsCompleteDevVAddr;
 
-       
+       /* Device accessible ReadOp2 Info */
+       IMG_DEV_VIRTADDR                sReadOps2CompleteDevVAddr;
+
+       /* handle to client mapping data (OS specific) */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hMappingInfo;
 
-       
+       /* handle to kernel sync info */
        IMG_SID                                 hKernelSyncInfo;
 #else
        IMG_HANDLE                                      hMappingInfo;
 
-       
+       /* handle to kernel sync info */
        IMG_HANDLE                                      hKernelSyncInfo;
 #endif
 
 } PVRSRV_CLIENT_SYNC_INFO, *PPVRSRV_CLIENT_SYNC_INFO;
 
+/*!
+ *****************************************************************************
+ * Resource locking structure
+ *****************************************************************************/
 typedef struct PVRSRV_RESOURCE_TAG
 {
        volatile IMG_UINT32 ui32Lock;
@@ -682,13 +770,18 @@ typedef struct PVRSRV_RESOURCE_TAG
 typedef PVRSRV_RESOURCE PVRSRV_RES_HANDLE;
 
 
+/* command complete callback pfn prototype */
 typedef IMG_VOID (*PFN_CMD_COMPLETE) (IMG_HANDLE);
 typedef IMG_VOID (**PPFN_CMD_COMPLETE) (IMG_HANDLE);
 
+/* private command handler prototype */
 typedef IMG_BOOL (*PFN_CMD_PROC) (IMG_HANDLE, IMG_UINT32, IMG_VOID*);
 typedef IMG_BOOL (**PPFN_CMD_PROC) (IMG_HANDLE, IMG_UINT32, IMG_VOID*);
 
 
+/*
+       rectangle structure required by Lock API
+*/
 typedef struct _IMG_RECT_
 {
        IMG_INT32       x0;
@@ -706,6 +799,7 @@ typedef struct _IMG_RECT_16_
 }IMG_RECT_16;
 
 
+/* common pfn between BC/DC */
 typedef PVRSRV_ERROR (*PFN_GET_BUFFER_ADDR)(IMG_HANDLE,
                                                                                        IMG_HANDLE,
                                                                                        IMG_SYS_PHYADDR**,
@@ -716,6 +810,9 @@ typedef PVRSRV_ERROR (*PFN_GET_BUFFER_ADDR)(IMG_HANDLE,
                                                                                        IMG_UINT32*);
 
 
+/*
+       Display dimension structure definition
+*/
 typedef struct DISPLAY_DIMS_TAG
 {
        IMG_UINT32      ui32ByteStride;
@@ -724,54 +821,66 @@ typedef struct DISPLAY_DIMS_TAG
 } DISPLAY_DIMS;
 
 
+/*
+       Display format structure definition
+*/
 typedef struct DISPLAY_FORMAT_TAG
 {
-       
+       /* pixel format type */
        PVRSRV_PIXEL_FORMAT             pixelformat;
 } DISPLAY_FORMAT;
 
+/*
+       Display Surface Attributes structure definition
+*/
 typedef struct DISPLAY_SURF_ATTRIBUTES_TAG
 {
-       
+       /* pixel format type */
        PVRSRV_PIXEL_FORMAT             pixelformat;
-       
+       /* dimensions information structure array */
        DISPLAY_DIMS                    sDims;
 } DISPLAY_SURF_ATTRIBUTES;
 
 
+/*
+       Display Mode information structure definition
+*/
 typedef struct DISPLAY_MODE_INFO_TAG
 {
-       
+       /* pixel format type */
        PVRSRV_PIXEL_FORMAT             pixelformat;
-       
+       /* dimensions information structure array */
        DISPLAY_DIMS                    sDims;
-       
+       /* refresh rate of the display */
        IMG_UINT32                              ui32RefreshHZ;
-       
+       /* OEM specific flags */
        IMG_UINT32                              ui32OEMFlags;
 } DISPLAY_MODE_INFO;
 
 
 
-#define MAX_DISPLAY_NAME_SIZE  (50) 
+#define MAX_DISPLAY_NAME_SIZE  (50) /* arbitrary choice! */
 
+/*
+       Display info structure definition
+*/
 typedef struct DISPLAY_INFO_TAG
 {
-       
+       /* max swapchains supported */
        IMG_UINT32 ui32MaxSwapChains;
-       
+       /* max buffers in a swapchain */
        IMG_UINT32 ui32MaxSwapChainBuffers;
-       
+       /* min swap interval supported */
        IMG_UINT32 ui32MinSwapInterval;
-       
+       /* max swap interval supported */
        IMG_UINT32 ui32MaxSwapInterval;
-       
+       /* physical dimensions of the display required for DPI calc. */
        IMG_UINT32 ui32PhysicalWidthmm;
        IMG_UINT32 ui32PhysicalHeightmm;
-       
+       /* display name */
        IMG_CHAR        szDisplayName[MAX_DISPLAY_NAME_SIZE];
 #if defined(SUPPORT_HW_CURSOR)
-       
+       /* cursor dimensions */
        IMG_UINT16      ui32CursorWidth;
        IMG_UINT16      ui32CursorHeight;
 #endif
@@ -781,7 +890,7 @@ typedef struct ACCESS_INFO_TAG
 {
        IMG_UINT32              ui32Size;
        IMG_UINT32      ui32FBPhysBaseAddress;
-       IMG_UINT32              ui32FBMemAvailable;                     
+       IMG_UINT32              ui32FBMemAvailable;                     /* size of usable FB memory */
        IMG_UINT32      ui32SysPhysBaseAddress;
        IMG_UINT32              ui32SysSize;
        IMG_UINT32              ui32DevIRQ;
@@ -790,6 +899,8 @@ typedef struct ACCESS_INFO_TAG
 
 
 #if defined(PDUMP_SUSPEND_IS_PER_THREAD)
+/** Present only on WinMobile 6.5 */
+
 typedef struct {
        IMG_UINT32 threadId;
        IMG_INT    suspendCount;
@@ -798,9 +909,13 @@ typedef struct {
 #define PVRSRV_PDUMP_SUSPEND_Q_NAME "PVRSRVPDumpSuspendMsgQ"
 #define PVRSRV_PDUMP_SUSPEND_Q_LENGTH 8
 
-#endif 
+#endif /* defined(PDUMP_SUSPEND_IS_PER_THREAD) */
 
 
+/*!
+ *****************************************************************************
+ * This structure is used for OS independent registry (profile) access
+ *****************************************************************************/
 typedef struct _PVRSRV_REGISTRY_INFO_
 {
     IMG_UINT32         ui32DevCookie;
@@ -821,8 +936,9 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVWriteRegistryString (PPVRSRV_REGISTRY_INFO psReg
 #define PVRSRV_BC_FLAGS_YUVCSC_BT601                   (0 << 1)
 #define PVRSRV_BC_FLAGS_YUVCSC_BT709                   (1 << 1)
 
-#define MAX_BUFFER_DEVICE_NAME_SIZE    (50) 
+#define MAX_BUFFER_DEVICE_NAME_SIZE    (50) /* arbitrary choice! */
 
+/* buffer information structure */
 typedef struct BUFFER_INFO_TAG
 {
        IMG_UINT32                      ui32BufferCount;
@@ -843,4 +959,7 @@ typedef enum _OVERLAY_DEINTERLACE_MODE_
        BOB_EVEN_NONINTERLEAVED
 } OVERLAY_DEINTERLACE_MODE;
 
-#endif 
+#endif /* __SERVICESEXT_H__ */
+/*****************************************************************************
+ End of file (servicesext.h)
+*****************************************************************************/
index d2ddff6..619e6e7 100644 (file)
@@ -1,56 +1,89 @@
-/**********************************************************************
+/*************************************************************************/ /*!
+@Title          
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+/* Each build option listed here is packed into a dword which
+ * provides up to 32 flags (or up to 28 flags plus a numeric
+ * value in the range 0-15 which corresponds to the number of
+ * cores minus one if SGX_FEATURE_MP is defined). The corresponding
+ * bit is set if the build option was enabled at compile time.
  *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
+ * In order to extract the enabled build flags the INTERNAL_TEST
+ * switch should be enabled in a client program which includes this
+ * header. Then the client can test specific build flags by reading
+ * the bit value at ##OPTIONNAME##_SET_OFFSET in SGX_BUILD_OPTIONS.
  *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+ * IMPORTANT: add new options to unused bits or define a new dword
+ * (e.g. SGX_BUILD_OPTIONS2) so that the bitfield remains backwards
+ * compatible.
+ */
+
 
 #if defined(DEBUG) || defined (INTERNAL_TEST)
 #define DEBUG_SET_OFFSET       OPTIONS_BIT0
 #define OPTIONS_BIT0           0x1U
 #else
 #define OPTIONS_BIT0           0x0
-#endif 
+#endif /* DEBUG */
 
 #if defined(PDUMP) || defined (INTERNAL_TEST)
 #define PDUMP_SET_OFFSET       OPTIONS_BIT1
 #define OPTIONS_BIT1           (0x1U << 1)
 #else
 #define OPTIONS_BIT1           0x0
-#endif 
+#endif /* PDUMP */
 
 #if defined(PVRSRV_USSE_EDM_STATUS_DEBUG) || defined (INTERNAL_TEST)
 #define PVRSRV_USSE_EDM_STATUS_DEBUG_SET_OFFSET                OPTIONS_BIT2
 #define OPTIONS_BIT2           (0x1U << 2)
 #else
 #define OPTIONS_BIT2           0x0
-#endif 
+#endif /* PVRSRV_USSE_EDM_STATUS_DEBUG */
 
 #if defined(SUPPORT_HW_RECOVERY) || defined (INTERNAL_TEST)
 #define SUPPORT_HW_RECOVERY_SET_OFFSET OPTIONS_BIT3
 #define OPTIONS_BIT3           (0x1U << 3)
 #else
 #define OPTIONS_BIT3           0x0
-#endif 
+#endif /* SUPPORT_HW_RECOVERY */
 
 
 
@@ -63,7 +96,7 @@
 #define OPTIONS_BIT4           (0x1U << 4)
 #else
 #define OPTIONS_BIT4           0x0
-#endif 
+#endif /* PVR_SECURE_HANDLES */
 #endif
 
 #if defined(SGX_BYPASS_SYSTEM_CACHE) || defined (INTERNAL_TEST)
 #define OPTIONS_BIT5           (0x1U << 5)
 #else
 #define OPTIONS_BIT5           0x0
-#endif 
+#endif /* SGX_BYPASS_SYSTEM_CACHE */
 
 #if defined(SGX_DMS_AGE_ENABLE) || defined (INTERNAL_TEST)
 #define SGX_DMS_AGE_ENABLE_SET_OFFSET  OPTIONS_BIT6
 #define OPTIONS_BIT6           (0x1U << 6)
 #else
 #define OPTIONS_BIT6           0x0
-#endif 
+#endif /* SGX_DMS_AGE_ENABLE */
 
 #if defined(SGX_FAST_DPM_INIT) || defined (INTERNAL_TEST)
 #define SGX_FAST_DPM_INIT_SET_OFFSET   OPTIONS_BIT8
 #define OPTIONS_BIT8           (0x1U << 8)
 #else
 #define OPTIONS_BIT8           0x0
-#endif 
+#endif /* SGX_FAST_DPM_INIT */
 
 #if defined(SGX_FEATURE_WRITEBACK_DCU) || defined (INTERNAL_TEST)
 #define SGX_FEATURE_DCU_SET_OFFSET     OPTIONS_BIT9
 #define OPTIONS_BIT9           (0x1U << 9)
 #else
 #define OPTIONS_BIT9           0x0
-#endif 
+#endif /* SGX_FEATURE_WRITEBACK_DCU */
 
 #if defined(SGX_FEATURE_MP) || defined (INTERNAL_TEST)
 #define SGX_FEATURE_MP_SET_OFFSET      OPTIONS_BIT10
 #define OPTIONS_BIT10          (0x1U << 10)
 #else
 #define OPTIONS_BIT10          0x0
-#endif 
+#endif /* SGX_FEATURE_MP */
 
-#if defined(SGX_FEATURE_MULTITHREADED_UKERNEL) || defined (INTERNAL_TEST)
-#define SGX_FEATURE_MULTITHREADED_UKERNEL_SET_OFFSET   OPTIONS_BIT11
-#define OPTIONS_BIT11          (0x1U << 11)
-#else
 #define OPTIONS_BIT11          0x0
-#endif 
-
 
 
 #if defined(SGX_FEATURE_OVERLAPPED_SPM) || defined (INTERNAL_TEST)
 #define OPTIONS_BIT12          (0x1U << 12)
 #else
 #define OPTIONS_BIT12          0x0
-#endif 
+#endif /* SGX_FEATURE_RENDER_TARGET_ARRAYS */
 
 
 #if defined(SGX_FEATURE_SYSTEM_CACHE) || defined (INTERNAL_TEST)
 #define OPTIONS_BIT13          (0x1U << 13)
 #else
 #define OPTIONS_BIT13          0x0
-#endif 
+#endif /* SGX_FEATURE_SYSTEM_CACHE */
 
 #if defined(SGX_SUPPORT_HWPROFILING) || defined (INTERNAL_TEST)
 #define SGX_SUPPORT_HWPROFILING_SET_OFFSET     OPTIONS_BIT14
 #define OPTIONS_BIT14          (0x1U << 14)
 #else
 #define OPTIONS_BIT14          0x0
-#endif 
+#endif /* SGX_SUPPORT_HWPROFILING */
 
 
 
 #define OPTIONS_BIT15          (0x1U << 15)
 #else
 #define OPTIONS_BIT15          0x0
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
 
 #if defined(SUPPORT_DISPLAYCONTROLLER_TILING) || defined (INTERNAL_TEST)
 #define SUPPORT_DISPLAYCONTROLLER_TILING_SET_OFFSET    OPTIONS_BIT16
 #define OPTIONS_BIT16          (0x1U << 16)
 #else
 #define OPTIONS_BIT16          0x0
-#endif 
+#endif /* SUPPORT_DISPLAYCONTROLLER_TILING */
 
 #if defined(SUPPORT_PERCONTEXT_PB) || defined (INTERNAL_TEST)
 #define SUPPORT_PERCONTEXT_PB_SET_OFFSET       OPTIONS_BIT17
 #define OPTIONS_BIT17          (0x1U << 17)
 #else
 #define OPTIONS_BIT17          0x0
-#endif 
+#endif /* SUPPORT_PERCONTEXT_PB */
 
 #if defined(SUPPORT_SGX_HWPERF) || defined (INTERNAL_TEST)
 #define SUPPORT_SGX_HWPERF_SET_OFFSET  OPTIONS_BIT18
 #define OPTIONS_BIT18          (0x1U << 18)
 #else
 #define OPTIONS_BIT18          0x0
-#endif 
+#endif /* SUPPORT_SGX_HWPERF */
 
 
 
 #define OPTIONS_BIT19          (0x1U << 19)
 #else
 #define OPTIONS_BIT19          0x0
-#endif 
+#endif /* SUPPORT_SGX_MMU_DUMMY_PAGE */
 
 #if defined(SUPPORT_SGX_PRIORITY_SCHEDULING) || defined (INTERNAL_TEST)
 #define SUPPORT_SGX_PRIORITY_SCHEDULING_SET_OFFSET     OPTIONS_BIT20
 #define OPTIONS_BIT20          (0x1U << 20)
 #else
 #define OPTIONS_BIT20          0x0
-#endif 
+#endif /* SUPPORT_SGX_PRIORITY_SCHEDULING */
 
 #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) || defined (INTERNAL_TEST)
 #define SUPPORT_SGX_LOW_LATENCY_SCHEDULING_SET_OFFSET  OPTIONS_BIT21
 #define OPTIONS_BIT21          (0x1U << 21)
 #else
 #define OPTIONS_BIT21          0x0
-#endif 
+#endif /* SUPPORT_SGX_LOW_LATENCY_SCHEDULING */
 
 #if defined(USE_SUPPORT_NO_TA3D_OVERLAP) || defined (INTERNAL_TEST)
 #define USE_SUPPORT_NO_TA3D_OVERLAP_SET_OFFSET OPTIONS_BIT22
 #define OPTIONS_BIT22          (0x1U << 22)
 #else
 #define OPTIONS_BIT22          0x0
-#endif 
+#endif /* USE_SUPPORT_NO_TA3D_OVERLAP */
 
 #if defined(SGX_FEATURE_MP) || defined (INTERNAL_TEST)
 #if defined(SGX_FEATURE_MP_CORE_COUNT)
 #define SGX_FEATURE_MP_CORE_COUNT_SET_OFFSET_3D        28UL
 #define SGX_FEATURE_MP_CORE_COUNT_SET_MASK             0xFF
 #endif
-#else 
+#else /* SGX_FEATURE_MP */
 #define OPTIONS_HIGHBYTE       0x0
-#endif 
+#endif /* SGX_FEATURE_MP */
 
 
 
index dcbafbf..bb8776a 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX KM API Header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Exported SGX API details
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __SGXAPI_KM_H__
 #define __SGXAPI_KM_H__
@@ -41,6 +57,11 @@ extern "C" {
        #endif
 #endif
 
+/******************************************************************************
+ Some defines...
+******************************************************************************/
+
+/* SGX Heap IDs, note: not all heaps are available to clients */
 #define SGX_UNDEFINED_HEAP_ID                                  (~0LU)
 #define SGX_GENERAL_HEAP_ID                                            0
 #define SGX_TADATA_HEAP_ID                                             1
@@ -58,18 +79,27 @@ extern "C" {
 #endif
 #if defined(SGX_FEATURE_2D_HARDWARE)
 #define SGX_2D_HEAP_ID                                                 12
-#else
-#if defined(FIX_HW_BRN_26915)
-#define SGX_CGBUFFER_HEAP_ID                                   13
 #endif
+#if defined(SUPPORT_MEMORY_TILING)
+#define SGX_VPB_TILED_HEAP_ID                  14
+#endif
+#if defined(SUPPORT_ION)
+#define SGX_ION_HEAP_ID                                                        15
 #endif
-#define SGX_MAX_HEAP_ID                                                        14
 
+#define SGX_MAX_HEAP_ID                                                        16
+
+/*
+ * Keep SGX_3DPARAMETERS_HEAP_ID as TQ full custom
+ * shaders need it to select which heap to write
+ * their ISP controll stream to.
+ */
 #if (defined(SUPPORT_PERCONTEXT_PB) || defined(SUPPORT_HYBRID_PB))
 #define SGX_3DPARAMETERS_HEAP_ID                       SGX_PERCONTEXT_3DPARAMETERS_HEAP_ID     
 #else
 #define SGX_3DPARAMETERS_HEAP_ID                       SGX_SHARED_3DPARAMETERS_HEAP_ID
 #endif
+/* Define for number of bytes between consecutive code base registers */
 #if defined(SGX543) || defined(SGX544) || defined(SGX554)
 #define SGX_USE_CODE_SEGMENT_RANGE_BITS                23
 #else
@@ -80,12 +110,18 @@ extern "C" {
 #define SGX_MAX_3D_STATUS_VALS 4
 
 #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS)
+/* sync info structure array size */
 #define SGX_MAX_TA_DST_SYNCS                   1
 #define SGX_MAX_TA_SRC_SYNCS                   1
 #define SGX_MAX_3D_SRC_SYNCS                   4
+/* note: there is implicitly 1 3D Dst Sync */
 #else
-#define SGX_MAX_SRC_SYNCS                              8
-#define SGX_MAX_DST_SYNCS                              1
+/* sync info structure array size */
+#define SGX_MAX_SRC_SYNCS_TA                           32
+#define SGX_MAX_DST_SYNCS_TA                           1
+/* note: there is implicitly 1 3D Dst Sync */
+#define SGX_MAX_SRC_SYNCS_TQ                           8
+#define SGX_MAX_DST_SYNCS_TQ                           1
 #endif
 
 
@@ -95,7 +131,7 @@ extern "C" {
 #else
 #define        PVRSRV_SGX_HWPERF_NUM_COUNTERS  9
 #define        PVRSRV_SGX_HWPERF_NUM_MISC_COUNTERS 8
-#endif 
+#endif /* SGX543 */
 
 #define PVRSRV_SGX_HWPERF_INVALID                                      0x1
 
@@ -165,6 +201,10 @@ extern "C" {
 #define PVRSRV_SGX_HWPERF_STATUS_MK_EXECUTION_ON       (1UL << 3)
 
 
+/*!
+ *****************************************************************************
+ * One entry in the HWPerf Circular Buffer. 
+ *****************************************************************************/
 typedef struct _PVRSRV_SGX_HWPERF_CB_ENTRY_
 {
        IMG_UINT32      ui32FrameNo;
@@ -174,12 +214,15 @@ typedef struct _PVRSRV_SGX_HWPERF_CB_ENTRY_
        IMG_UINT32      ui32Ordinal;
        IMG_UINT32      ui32Info;
        IMG_UINT32      ui32Clocksx16;
-               
+       /* NOTE: There should always be at least as many 3D cores as TA cores. */       
        IMG_UINT32      ui32Counters[SGX_FEATURE_MP_CORE_COUNT_3D][PVRSRV_SGX_HWPERF_NUM_COUNTERS];
        IMG_UINT32      ui32MiscCounters[SGX_FEATURE_MP_CORE_COUNT_3D][PVRSRV_SGX_HWPERF_NUM_MISC_COUNTERS];
 } PVRSRV_SGX_HWPERF_CB_ENTRY;
 
 
+/*
+       Status values control structure
+*/
 typedef struct _CTL_STATUS_
 {
        IMG_DEV_VIRTADDR        sStatusDevAddr;
@@ -187,6 +230,9 @@ typedef struct _CTL_STATUS_
 } CTL_STATUS;
 
 
+/*!
+       List of possible requests/commands to SGXGetMiscInfo()
+*/
 typedef enum _SGX_MISC_INFO_REQUEST_
 {
        SGX_MISC_INFO_REQUEST_CLOCKSPEED = 0,
@@ -195,14 +241,15 @@ typedef enum _SGX_MISC_INFO_REQUEST_
 #if defined(SUPPORT_SGX_EDM_MEMORY_DEBUG)
        SGX_MISC_INFO_REQUEST_MEMREAD,
        SGX_MISC_INFO_REQUEST_MEMCOPY,
-#endif 
+#endif /* SUPPORT_SGX_EDM_MEMORY_DEBUG */
        SGX_MISC_INFO_REQUEST_SET_HWPERF_STATUS,
 #if defined(SGX_FEATURE_DATA_BREAKPOINTS)
        SGX_MISC_INFO_REQUEST_SET_BREAKPOINT,
        SGX_MISC_INFO_REQUEST_POLL_BREAKPOINT,
        SGX_MISC_INFO_REQUEST_RESUME_BREAKPOINT,
-#endif 
+#endif /* SGX_FEATURE_DATA_BREAKPOINTS */
        SGX_MISC_INFO_DUMP_DEBUG_INFO,
+       SGX_MISC_INFO_DUMP_DEBUG_INFO_FORCE_REGS,
        SGX_MISC_INFO_PANIC,
        SGX_MISC_INFO_REQUEST_SPM,
        SGX_MISC_INFO_REQUEST_ACTIVEPOWER,
@@ -211,66 +258,84 @@ typedef enum _SGX_MISC_INFO_REQUEST_
 } SGX_MISC_INFO_REQUEST;
 
 
+/******************************************************************************
+ * Struct for passing SGX core rev/features from ukernel to driver.
+ * This is accessed from the kernel part of the driver and microkernel; it is
+ * only accessed in user space during buffer allocation in srvinit.
+ ******************************************************************************/
 typedef struct _PVRSRV_SGX_MISCINFO_FEATURES
 {
-       IMG_UINT32                      ui32CoreRev;    
-       IMG_UINT32                      ui32CoreID;             
-       IMG_UINT32                      ui32DDKVersion; 
-       IMG_UINT32                      ui32DDKBuild;   
-       IMG_UINT32                      ui32CoreIdSW;   
-       IMG_UINT32                      ui32CoreRevSW;  
-       IMG_UINT32                      ui32BuildOptions;       
+       IMG_UINT32                      ui32CoreRev;    /*!< SGX Core revision from HW register */
+       IMG_UINT32                      ui32CoreID;             /*!< SGX Core ID from HW register */
+       IMG_UINT32                      ui32DDKVersion; /*!< software DDK version */
+       IMG_UINT32                      ui32DDKBuild;   /*!< software DDK build no. */
+       IMG_UINT32                      ui32CoreIdSW;   /*!< software core version (ID), e.g. SGX535, SGX540 */
+       IMG_UINT32                      ui32CoreRevSW;  /*!< software core revision */
+       IMG_UINT32                      ui32BuildOptions;       /*!< build options bit-field */
 #if defined(SUPPORT_SGX_EDM_MEMORY_DEBUG)
-       IMG_UINT32                      ui32DeviceMemValue;             
+       IMG_UINT32                      ui32DeviceMemValue;             /*!< device mem value read from ukernel */
 #endif
 #if defined(PVRSRV_USSE_EDM_STATUS_DEBUG)
-       IMG_DEV_VIRTADDR        sDevVAEDMStatusBuffer;  
-       IMG_PVOID                       pvEDMStatusBuffer;              
+       IMG_DEV_VIRTADDR        sDevVAEDMStatusBuffer;  /*!< DevVAddr of the EDM status buffer */
+       IMG_PVOID                       pvEDMStatusBuffer;              /*!< CPUVAddr of the EDM status buffer */
 #endif
 } PVRSRV_SGX_MISCINFO_FEATURES;
 
 
+/******************************************************************************
+ * Struct for getting lock-up stats from the kernel driver
+ ******************************************************************************/
 typedef struct _PVRSRV_SGX_MISCINFO_LOCKUPS
 {
-       IMG_UINT32                      ui32HostDetectedLockups; 
-       IMG_UINT32                      ui32uKernelDetectedLockups; 
+       IMG_UINT32                      ui32HostDetectedLockups; /*!< Host timer detected lockups */
+       IMG_UINT32                      ui32uKernelDetectedLockups; /*!< Microkernel detected lockups */
 } PVRSRV_SGX_MISCINFO_LOCKUPS;
 
 
+/******************************************************************************
+ * Struct for getting lock-up stats from the kernel driver
+ ******************************************************************************/
 typedef struct _PVRSRV_SGX_MISCINFO_ACTIVEPOWER
 {
-       IMG_UINT32                      ui32NumActivePowerEvents; 
+       IMG_UINT32                      ui32NumActivePowerEvents; /*!< active power events */
 } PVRSRV_SGX_MISCINFO_ACTIVEPOWER;
 
 
+/******************************************************************************
+ * Struct for getting SPM stats fro the kernel driver
+ ******************************************************************************/
 typedef struct _PVRSRV_SGX_MISCINFO_SPM
 {
-       IMG_HANDLE                      hRTDataSet;                             
-       IMG_UINT32                      ui32NumOutOfMemSignals; 
-       IMG_UINT32                      ui32NumSPMRenders;      
+       IMG_HANDLE                      hRTDataSet;                             /*!< render target data set handle returned from SGXAddRenderTarget */
+       IMG_UINT32                      ui32NumOutOfMemSignals; /*!< Number of Out of Mem Signals */
+       IMG_UINT32                      ui32NumSPMRenders;      /*!< Number of SPM renders */
 } PVRSRV_SGX_MISCINFO_SPM;
 
 
 #if defined(SGX_FEATURE_DATA_BREAKPOINTS)
+/*!
+ ******************************************************************************
+ * Structure for SGX break points control
+ *****************************************************************************/
 typedef struct _SGX_BREAKPOINT_INFO
 {
-       
+       /* set/clear BP boolean */
        IMG_BOOL                                        bBPEnable;
-       
+       /* Index of BP to set */
        IMG_UINT32                                      ui32BPIndex;
-       
+       /* On which DataMaster(s) should the breakpoint fire? */
        IMG_UINT32                  ui32DataMasterMask;
-       
+       /* DevVAddr of BP to set */
        IMG_DEV_VIRTADDR                        sBPDevVAddr, sBPDevVAddrEnd;
-       
+       /* Whether or not the desired breakpoint will be trapped */
        IMG_BOOL                    bTrapped;
-       
+       /* Will the requested breakpoint fire for reads? */
        IMG_BOOL                    bRead;
-       
+       /* Will the requested breakpoint fire for writes? */
        IMG_BOOL                    bWrite;
-       
+       /* Has a breakpoint been trapped? */
        IMG_BOOL                    bTrappedBP;
-       
+       /* Extra information recorded about a trapped breakpoint */
        IMG_UINT32                  ui32CoreNum;
        IMG_DEV_VIRTADDR            sTrappedBPDevVAddr;
        IMG_UINT32                  ui32TrappedBPBurstLength;
@@ -278,38 +343,50 @@ typedef struct _SGX_BREAKPOINT_INFO
        IMG_UINT32                  ui32TrappedBPDataMaster;
        IMG_UINT32                  ui32TrappedBPTag;
 } SGX_BREAKPOINT_INFO;
-#endif 
+#endif /* SGX_FEATURE_DATA_BREAKPOINTS */
 
 
+/*!
+ ******************************************************************************
+ * Structure for setting the hardware performance status
+ *****************************************************************************/
 typedef struct _PVRSRV_SGX_MISCINFO_SET_HWPERF_STATUS
 {
-       
+       /* See PVRSRV_SGX_HWPERF_STATUS_* */
        IMG_UINT32      ui32NewHWPerfStatus;
        
        #if defined(SGX_FEATURE_EXTENDED_PERF_COUNTERS)
-       
+       /* Specifies the HW's active group selectors */
        IMG_UINT32      aui32PerfGroup[PVRSRV_SGX_HWPERF_NUM_COUNTERS];
-       
+       /* Specifies the HW's active bit selectors */
        IMG_UINT32      aui32PerfBit[PVRSRV_SGX_HWPERF_NUM_COUNTERS];
+       /* Specifies the HW's counter bit selectors */
+       IMG_UINT32      ui32PerfCounterBitSelect;
+       /* Specifies the HW's sum_mux selectors */
+       IMG_UINT32      ui32PerfSumMux;
        #else
-       
+       /* Specifies the HW's active group */
        IMG_UINT32      ui32PerfGroup;
-       #endif 
+       #endif /* SGX_FEATURE_EXTENDED_PERF_COUNTERS */
 } PVRSRV_SGX_MISCINFO_SET_HWPERF_STATUS;
 
 
+/*!
+ ******************************************************************************
+ * Structure for misc SGX commands in services
+ *****************************************************************************/
 typedef struct _SGX_MISC_INFO_
 {
-       SGX_MISC_INFO_REQUEST   eRequest;       
+       SGX_MISC_INFO_REQUEST   eRequest;       /*!< Command request to SGXGetMiscInfo() */
        IMG_UINT32                              ui32Padding;
 #if defined(SUPPORT_SGX_EDM_MEMORY_DEBUG)
-       IMG_DEV_VIRTADDR                        sDevVAddrSrc;           
-       IMG_DEV_VIRTADDR                        sDevVAddrDest;          
-       IMG_HANDLE                                      hDevMemContext;         
+       IMG_DEV_VIRTADDR                        sDevVAddrSrc;           /*!< dev virtual addr for mem read */
+       IMG_DEV_VIRTADDR                        sDevVAddrDest;          /*!< dev virtual addr for mem write */
+       IMG_HANDLE                                      hDevMemContext;         /*!< device memory context for mem debug */
 #endif
        union
        {
-               IMG_UINT32      reserved;       
+               IMG_UINT32      reserved;       /*!< Unused: ensures valid code in the case everything else is compiled out */
                PVRSRV_SGX_MISCINFO_FEATURES                                            sSGXFeatures;
                IMG_UINT32                                                                                      ui32SGXClockSpeed;
                PVRSRV_SGX_MISCINFO_ACTIVEPOWER                                         sActivePower;
@@ -323,12 +400,19 @@ typedef struct _SGX_MISC_INFO_
 } SGX_MISC_INFO;
 
 #if defined(SGX_FEATURE_2D_HARDWARE)
+/*
+ * The largest number of source sync objects that can be associated with a blit
+ * command.  Allows for src, pattern, and mask
+ */
 #define PVRSRV_MAX_BLT_SRC_SYNCS               3
 #endif
 
 
 #define SGX_KICKTA_DUMPBITMAP_MAX_NAME_LENGTH          256
 
+/*
+       Structure for dumping bitmaps
+*/
 typedef struct _SGX_KICKTA_DUMPBITMAP_
 {
        IMG_DEV_VIRTADDR        sDevBaseAddr;
@@ -343,9 +427,13 @@ typedef struct _SGX_KICKTA_DUMPBITMAP_
 
 #define PVRSRV_SGX_PDUMP_CONTEXT_MAX_BITMAP_ARRAY_SIZE (16)
 
+/*!
+ ******************************************************************************
+ * Data required only when dumping parameters
+ *****************************************************************************/
 typedef struct _PVRSRV_SGX_PDUMP_CONTEXT_
 {
-       
+       /* cache control word for micro kernel cache flush/invalidates */
        IMG_UINT32                                              ui32CacheControl;
 
 } PVRSRV_SGX_PDUMP_CONTEXT;
@@ -354,11 +442,11 @@ typedef struct _PVRSRV_SGX_PDUMP_CONTEXT_
 #if !defined (SUPPORT_SID_INTERFACE)
 typedef struct _SGX_KICKTA_DUMP_ROFF_
 {
-       IMG_HANDLE                      hKernelMemInfo;                                         
-       IMG_UINT32                      uiAllocIndex;                                           
-       IMG_UINT32                      ui32Offset;                                                     
-       IMG_UINT32                      ui32Value;                                                      
-       IMG_PCHAR                       pszName;                                                        
+       IMG_HANDLE                      hKernelMemInfo;                                         /*< Buffer handle */
+       IMG_UINT32                      uiAllocIndex;                                           /*< Alloc index for LDDM */
+       IMG_UINT32                      ui32Offset;                                                     /*< Byte offset to value to dump */
+       IMG_UINT32                      ui32Value;                                                      /*< Actual value to dump */
+       IMG_PCHAR                       pszName;                                                        /*< Name of buffer */
 } SGX_KICKTA_DUMP_ROFF, *PSGX_KICKTA_DUMP_ROFF;
 #endif
 
@@ -369,18 +457,24 @@ typedef struct _SGX_KICKTA_DUMP_BUFFER_
 #endif
 {
        IMG_UINT32                      ui32SpaceUsed;
-       IMG_UINT32                      ui32Start;                                                      
-       IMG_UINT32                      ui32End;                                                        
-       IMG_UINT32                      ui32BufferSize;                                         
-       IMG_UINT32                      ui32BackEndLength;                                      
+       IMG_UINT32                      ui32Start;                                                      /*< Byte offset of start to dump */
+       IMG_UINT32                      ui32End;                                                        /*< Byte offset of end of dump (non-inclusive) */
+       IMG_UINT32                      ui32BufferSize;                                         /*< Size of buffer */
+       IMG_UINT32                      ui32BackEndLength;                                      /*< Size of back end portion, if End < Start */
        IMG_UINT32                      uiAllocIndex;
-       IMG_HANDLE                      hKernelMemInfo;                                         
+       IMG_HANDLE                      hKernelMemInfo;                                         /*< MemInfo handle for the circular buffer */
        IMG_PVOID                       pvLinAddr;
 #if defined(SUPPORT_SGX_NEW_STATUS_VALS)
-       IMG_HANDLE                      hCtrlKernelMemInfo;                                     
-       IMG_DEV_VIRTADDR        sCtrlDevVAddr;                                          
+       IMG_HANDLE                      hCtrlKernelMemInfo;                                     /*< MemInfo handle for the control structure of the
+                                                                                                                               circular buffer */
+       IMG_DEV_VIRTADDR        sCtrlDevVAddr;                                          /*< Device virtual address of the memory in the 
+                                                                                                                               control structure to be checked */
+#endif
+       IMG_PCHAR                       pszName;                                                        /*< Name of buffer */
+
+#if defined (__QNXNTO__)
+       IMG_UINT32          ui32NameLength;                     /*< Number of characters in buffer name */
 #endif
-       IMG_PCHAR                       pszName;                                                        
 #if defined (SUPPORT_SID_INTERFACE)
 } SGX_KICKTA_DUMP_BUFFER_KM, *PSGX_KICKTA_DUMP_BUFFER_KM;
 #else
@@ -389,25 +483,29 @@ typedef struct _SGX_KICKTA_DUMP_BUFFER_
 
 #if !defined (SUPPORT_SID_INTERFACE)
 #ifdef PDUMP
+/*
+       PDUMP version of above kick structure
+*/
 typedef struct _SGX_KICKTA_PDUMP_
 {
-       
+       // Bitmaps to dump
        PSGX_KICKTA_DUMPBITMAP          psPDumpBitmapArray;
        IMG_UINT32                                              ui32PDumpBitmapSize;
 
-       
+       // Misc buffers to dump (e.g. TA, PDS etc..)
        PSGX_KICKTA_DUMP_BUFFER psBufferArray;
        IMG_UINT32                                              ui32BufferArraySize;
 
-       
+       // Roffs to dump
        PSGX_KICKTA_DUMP_ROFF           psROffArray;
        IMG_UINT32                                              ui32ROffArraySize;
 } SGX_KICKTA_PDUMP, *PSGX_KICKTA_PDUMP;
-#endif 
-#endif 
+#endif /* PDUMP */
+#endif /* #if !defined (SUPPORT_SID_INTERFACE) */
 
 #if defined(TRANSFER_QUEUE)
 #if defined(SGX_FEATURE_2D_HARDWARE)
+/* Maximum size of ctrl stream for 2d blit command (in 32 bit words) */
 #define SGX_MAX_2D_BLIT_CMD_SIZE               26
 #define SGX_MAX_2D_SRC_SYNC_OPS                        3
 #endif
@@ -419,5 +517,8 @@ typedef struct _SGX_KICKTA_PDUMP_
 }
 #endif
 
-#endif 
+#endif /* __SGXAPI_KM_H__ */
 
+/******************************************************************************
+ End of file (sgxapi_km.h)
+******************************************************************************/
index df79e2f..46b89d2 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX kernel services structues/functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    SGX initialisation script definitions.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __SGXSCRIPT_H__
 #define __SGXSCRIPT_H__
 
@@ -38,6 +53,7 @@ typedef       enum _SGX_INIT_OPERATION
 {
        SGX_INIT_OP_ILLEGAL = 0,
        SGX_INIT_OP_WRITE_HW_REG,
+       SGX_INIT_OP_READ_HW_REG,
 #if defined(PDUMP)
        SGX_INIT_OP_PDUMP_HW_REG,
 #endif
@@ -52,6 +68,10 @@ typedef union _SGX_INIT_COMMAND
                IMG_UINT32 ui32Offset;
                IMG_UINT32 ui32Value;
        } sWriteHWReg;
+       struct {
+               SGX_INIT_OPERATION eOp;
+               IMG_UINT32 ui32Offset;
+       } sReadHWReg;
 #if defined(PDUMP)
        struct {
                SGX_INIT_OPERATION eOp;
@@ -59,11 +79,6 @@ typedef union _SGX_INIT_COMMAND
                IMG_UINT32 ui32Value;
        } sPDumpHWReg;
 #endif
-#if defined(FIX_HW_BRN_22997) && defined(FIX_HW_BRN_23030) && defined(SGX_FEATURE_HOST_PORT)                   
-       struct {
-               SGX_INIT_OPERATION eOp;
-       } sWorkaroundBRN22997;
-#endif 
 } SGX_INIT_COMMAND;
 
 typedef struct _SGX_INIT_SCRIPTS_
@@ -77,5 +92,8 @@ typedef struct _SGX_INIT_SCRIPTS_
 }
 #endif
 
-#endif 
+#endif /* __SGXSCRIPT_H__ */
 
+/*****************************************************************************
+ End of file (sgxscript.h)
+*****************************************************************************/
index 04938c1..8f5720e 100644 (file)
@@ -1,28 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
-
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 ccflags-y += -I$(TOP)/services4/3rdparty/bufferclass_example
 
 bc_example-y += \
index cb001fd..f2e44a6 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 modules := bufferclass_example
 
index 5ac75ee..2669888 100644 (file)
@@ -1,29 +1,68 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          bufferclass_example kernel driver
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with a 3rd Party 'buffer device'.  It is NOT a specification for
+ a 'buffer device' driver, rather a specification to extend the API for a
+ pre-existing driver for the 'buffer device' hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying buffer device hardware, 
+ allowing the client drivers to indirectly control the buffer device hardware
+ and access its associated memory.
+ Functions of the API include
+ - query buffer device surface attributes (width, height, stride, pixel format, 
+ CPU physical and virtual address)
+
+ Note: having queried surface attributes the client drivers are able to map the
+ buffer device memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the buffer device surface handle.
+
+ This code is intended to be an example of how a pre-existing buffer device
+ driver may be extended to support the 3rd Party buffer device interface to 
+ POWERVR Services
+ - IMG is not providing a buffer device driver implementation.
+ **************************************************************************/
 #if defined(__linux__)
 #include <linux/string.h>
 #else
 
 #define BUFFERCLASS_DEVICE_NAME "Example Bufferclass Device (SW)"
 
+/* top level 'hook ptr' */
 static void *gpvAnchor = NULL;
 static PFN_BC_GET_PVRJTABLE pfnGetPVRJTable = IMG_NULL;
 
+/*
+       Kernel services is a kernel module and must be loaded first.
+       This driver is also a kernel module and must be loaded after the pvr services module.
+       This driver should be able to retrieve the
+       address of the services PVRGetBufferClassJTable from (the already loaded)
+       kernel services module.
+*/
+
+/* returns anchor pointer */
 BC_EXAMPLE_DEVINFO * GetAnchorPtr(void)
 {
        return (BC_EXAMPLE_DEVINFO *)gpvAnchor;
 }
 
+/* sets anchor pointer */
 static void SetAnchorPtr(BC_EXAMPLE_DEVINFO *psDevInfo)
 {
        gpvAnchor = (void *)psDevInfo;
 }
 
 
+/* Open device function, called from services */
 static PVRSRV_ERROR OpenBCDevice(IMG_UINT32 ui32DeviceID, IMG_HANDLE *phDevice)
 {
        BC_EXAMPLE_DEVINFO *psDevInfo;
        
-       
-
-
+       /*
+               bufferclass_example manages only one BufferClass device
+               therefore there is no need to track ID numbers.
+       */
        UNREFERENCED_PARAMETER(ui32DeviceID);
 
        psDevInfo = GetAnchorPtr();
 
-       
+       /* return handle to the devinfo */
        *phDevice = (IMG_HANDLE)psDevInfo;
 
        return (PVRSRV_OK);
 }
 
 
+/* Close device function, called from services */
 static PVRSRV_ERROR CloseBCDevice(IMG_UINT32 ui32DeviceID, IMG_HANDLE hDevice)
 {
        UNREFERENCED_PARAMETER(hDevice);
@@ -75,6 +128,8 @@ static PVRSRV_ERROR CloseBCDevice(IMG_UINT32 ui32DeviceID, IMG_HANDLE hDevice)
        return (PVRSRV_OK);
 }
 
+/* Passes in the sync data for a buffer, and returns the handle */
+/* called from services */
 static PVRSRV_ERROR GetBCBuffer(IMG_HANDLE          hDevice,
                                 IMG_UINT32          ui32BufferNumber,
                                 PVRSRV_SYNC_DATA   *psSyncData,
@@ -103,6 +158,7 @@ static PVRSRV_ERROR GetBCBuffer(IMG_HANDLE          hDevice,
 }
 
 
+/* get buffer info function, called from services */
 static PVRSRV_ERROR GetBCInfo(IMG_HANDLE hDevice, BUFFER_INFO *psBCInfo)
 {
        BC_EXAMPLE_DEVINFO      *psDevInfo;
@@ -120,6 +176,7 @@ static PVRSRV_ERROR GetBCInfo(IMG_HANDLE hDevice, BUFFER_INFO *psBCInfo)
 }
 
 
+/* get buffer address function, called from services */
 static PVRSRV_ERROR GetBCBufferAddr(IMG_HANDLE      hDevice,
                                     IMG_HANDLE      hBuffer,
                                     IMG_SYS_PHYADDR **ppsSysAddr,
@@ -157,55 +214,67 @@ static PVRSRV_ERROR GetBCBufferAddr(IMG_HANDLE      hDevice,
 }
 
 
+/* 
+ *  Register the device with services module srvkm.
+ *  This should only be done once at boot time.
+ */
 BCE_ERROR BC_Example_Register(void)
 {
        BC_EXAMPLE_DEVINFO      *psDevInfo;
 
-       
-
-
-
-       
+       /*
+               - connect to services
+               - register with services
+               - allocate and setup private data structure
+       */
 
 
+       /*
+               in kernel driver, data structures must be anchored to something for subsequent retrieval
+               this may be a single global pointer or TLS or something else - up to you
+               call API to retrieve this ptr
+       */
 
-       
-
+       /*
+               get the anchor pointer 
+       */
        psDevInfo = GetAnchorPtr();
 
        if (psDevInfo == NULL)
        {
-               
+               /* allocate device info. structure */
                psDevInfo = (BC_EXAMPLE_DEVINFO *)BCAllocKernelMem(sizeof(BC_EXAMPLE_DEVINFO));
 
                if(!psDevInfo)
                {
-                       return (BCE_ERROR_OUT_OF_MEMORY);
+                       return (BCE_ERROR_OUT_OF_MEMORY);/* failure */
                }
 
-               
+               /* set the top-level anchor */
                SetAnchorPtr((void*)psDevInfo);
 
-               
+               /* set ref count */
                psDevInfo->ulRefCount = 0;
 
        
                if(BCOpenPVRServices(&psDevInfo->hPVRServices) != BCE_OK)
                {
-                       return (BCE_ERROR_INIT_FAILURE);
+                       return (BCE_ERROR_INIT_FAILURE);/* failure */
                }
                if(BCGetLibFuncAddr (psDevInfo->hPVRServices, "PVRGetBufferClassJTable", &pfnGetPVRJTable) != BCE_OK)
                {
-                       return (BCE_ERROR_INIT_FAILURE);
+                       return (BCE_ERROR_INIT_FAILURE);/* failure */
                }
 
-               
+               /* got the kernel services function table */
                if(!(*pfnGetPVRJTable)(&psDevInfo->sPVRJTable))
                {
-                       return (BCE_ERROR_INIT_FAILURE);
+                       return (BCE_ERROR_INIT_FAILURE);/* failure */
                }
 
-               
+               /*
+                       Setup the devinfo
+               */
 
                psDevInfo->ulNumBuffers = 0;
 
@@ -213,10 +282,10 @@ BCE_ERROR BC_Example_Register(void)
 
                if(!psDevInfo->psSystemBuffer)
                {
-                       return (BCE_ERROR_OUT_OF_MEMORY);
+                       return (BCE_ERROR_OUT_OF_MEMORY);/* failure */
                }
 
-               
+               /* Setup Buffer Info */
                psDevInfo->sBufferInfo.pixelformat        = PVRSRV_PIXEL_FORMAT_UNKNOWN;
                psDevInfo->sBufferInfo.ui32Width          = 0;
                psDevInfo->sBufferInfo.ui32Height         = 0;
@@ -227,8 +296,9 @@ BCE_ERROR BC_Example_Register(void)
                
                strncpy(psDevInfo->sBufferInfo.szDeviceName, BUFFERCLASS_DEVICE_NAME, MAX_BUFFER_DEVICE_NAME_SIZE);
 
-               
-
+               /*
+                       Bsetup the BC Jtable so SRVKM can call into this driver
+               */
                psDevInfo->sBCJTable.ui32TableSize    = sizeof(PVRSRV_BC_SRV2BUFFER_KMJTABLE);
                psDevInfo->sBCJTable.pfnOpenBCDevice  = OpenBCDevice;
                psDevInfo->sBCJTable.pfnCloseBCDevice = CloseBCDevice;
@@ -237,52 +307,55 @@ BCE_ERROR BC_Example_Register(void)
                psDevInfo->sBCJTable.pfnGetBufferAddr = GetBCBufferAddr;
 
 
-               
-               
+               /* register device with services and retrieve device index */
+               /* This example only registers 1 device, but for multiple buffer streams, register more devices */
                if(psDevInfo->sPVRJTable.pfnPVRSRVRegisterBCDevice (&psDevInfo->sBCJTable,
                                                                                                                        (IMG_UINT32*)&psDevInfo->ulDeviceID ) != PVRSRV_OK)
                {
-                       return (BCE_ERROR_DEVICE_REGISTER_FAILED);
+                       return (BCE_ERROR_DEVICE_REGISTER_FAILED);/* failure */
                }
        }
 
-       
+       /* increment the ref count */
        psDevInfo->ulRefCount++;
 
-       
+       /* return success */
        return (BCE_OK);
 }
 
+/* 
+ *  Unregister the device with services module srvkm.
+ */
 BCE_ERROR BC_Example_Unregister(void)
 {
        BC_EXAMPLE_DEVINFO *psDevInfo;
 
        psDevInfo = GetAnchorPtr();
 
-       
+       /* check DevInfo has been setup */
        if (psDevInfo == NULL)
        {
-               return (BCE_ERROR_GENERIC);
+               return (BCE_ERROR_GENERIC);/* failure */
        }
-       
+       /* decrement ref count */
        psDevInfo->ulRefCount--;
 
        if (psDevInfo->ulRefCount == 0)
        {
-               
+               /* all references gone - de-init device information */
                PVRSRV_BC_BUFFER2SRV_KMJTABLE   *psJTable = &psDevInfo->sPVRJTable;
 
 
-               
+               /* Remove the device from kernel services device register */
                if (psJTable->pfnPVRSRVRemoveBCDevice(psDevInfo->ulDeviceID) != PVRSRV_OK)
                {
-                       return (BCE_ERROR_GENERIC);
+                       return (BCE_ERROR_GENERIC);/* failure */
                }
 
                if (BCClosePVRServices(psDevInfo->hPVRServices) != BCE_OK)
                {
                        psDevInfo->hPVRServices = NULL;
-                       return (BCE_ERROR_GENERIC);
+                       return (BCE_ERROR_GENERIC);/* failure */
                }
 
                if (psDevInfo->psSystemBuffer)
@@ -290,18 +363,21 @@ BCE_ERROR BC_Example_Unregister(void)
                        BCFreeKernelMem(psDevInfo->psSystemBuffer);
                }
 
-               
+               /* de-allocate data structure */
                BCFreeKernelMem(psDevInfo);
 
-               
+               /* clear the top-level anchor */
                SetAnchorPtr(NULL);
        }
 
-       
+       /* return success */
        return (BCE_OK);
 }
 
 
+/* 
+ * Create shared buffers. 
+ */
 BCE_ERROR BC_Example_Buffers_Create(void)
 {
        BC_EXAMPLE_DEVINFO  *psDevInfo;
@@ -316,21 +392,24 @@ BCE_ERROR BC_Example_Buffers_Create(void)
 
        IMG_UINT32 ui32MaxWidth = 320 * 4;
 
-       
-
+       /*
+               get the anchor pointer 
+       */
        psDevInfo = GetAnchorPtr();
        if (psDevInfo == NULL)
        {
-               
+               /* 
+                * This device was not correctly registered/created. 
+                */
                return (BCE_ERROR_DEVICE_REGISTER_FAILED);
        }
        if (psDevInfo->ulNumBuffers)
        {
-               
+               /* Buffers already allocated */
                return (BCE_ERROR_GENERIC);
        }
                
-       
+       /* Setup Buffer Info */
        psDevInfo->sBufferInfo.pixelformat        = BC_EXAMPLE_PIXELFORMAT;
        psDevInfo->sBufferInfo.ui32Width          = ui32Width;
        psDevInfo->sBufferInfo.ui32Height         = ui32Height;
@@ -344,15 +423,15 @@ BCE_ERROR BC_Example_Buffers_Create(void)
 
                if(psDevInfo->sBufferInfo.pixelformat == PVRSRV_PIXEL_FORMAT_NV12)
                {
-                       
+                       /* Second plane is quarter size, but 2bytes per pixel */
                        ulSize += ((ui32ByteStride >> 1) * (ui32Height >> 1) << 1);
                }
-               else if(psDevInfo->sBufferInfo.pixelformat == PVRSRV_PIXEL_FORMAT_I420)
+               else if(psDevInfo->sBufferInfo.pixelformat == PVRSRV_PIXEL_FORMAT_YV12)
                {
-                       
+                       /* Second plane is quarter size, but 1byte per pixel */
                        ulSize += (ui32ByteStride >> 1) * (ui32Height >> 1);
                        
-                       
+                       /* third plane is quarter size, but 1byte per pixel */
                        ulSize += (ui32ByteStride >> 1) * (ui32Height >> 1);
                }
 
@@ -365,7 +444,7 @@ BCE_ERROR BC_Example_Buffers_Create(void)
                        break;
                }
 #else
-               
+               /* Setup system buffer */
                if (BCAllocContigMemory(ulSize,
                                        &psDevInfo->psSystemBuffer[i].hMemHandle,
                                        &psDevInfo->psSystemBuffer[i].sCPUVAddr,
@@ -385,8 +464,9 @@ BCE_ERROR BC_Example_Buffers_Create(void)
 
        psDevInfo->sBufferInfo.ui32BufferCount = (IMG_UINT32)psDevInfo->ulNumBuffers;
 
-       
-
+       /*
+               Bsetup the BC Jtable so SRVKM can call into this driver
+       */
        psDevInfo->sBCJTable.ui32TableSize    = sizeof(PVRSRV_BC_SRV2BUFFER_KMJTABLE);
        psDevInfo->sBCJTable.pfnOpenBCDevice  = OpenBCDevice;
        psDevInfo->sBCJTable.pfnCloseBCDevice = CloseBCDevice;
@@ -396,13 +476,13 @@ BCE_ERROR BC_Example_Buffers_Create(void)
        
 
 
-       
+       /* Update buffer's parameters for reconfiguration next time */
        if (ui32Width < ui32MaxWidth)
        {
                switch(pixelformat)
                {
                    case PVRSRV_PIXEL_FORMAT_NV12:
-                   case PVRSRV_PIXEL_FORMAT_I420:
+                   case PVRSRV_PIXEL_FORMAT_YV12:
                        {
                            ui32Width += 320;
                                ui32Height += 160;
@@ -439,11 +519,14 @@ BCE_ERROR BC_Example_Buffers_Create(void)
                ui32ByteStride = BC_EXAMPLE_STRIDE;
        }
 
-       
+       /* return success */
        return (BCE_OK);
 }
 
 
+/*
+ * Destroy shared buffers.
+ */
 BCE_ERROR BC_Example_Buffers_Destroy(void)
 {
        BC_EXAMPLE_DEVINFO *psDevInfo;
@@ -451,16 +534,18 @@ BCE_ERROR BC_Example_Buffers_Destroy(void)
 
        psDevInfo = GetAnchorPtr();
 
-       
+       /* check DevInfo has been setup */
        if (psDevInfo == NULL)
        {
-               
-
+               /* 
+                  This device was not correctly registered/created. 
+                */
                return (BCE_ERROR_DEVICE_REGISTER_FAILED);
        }
 
-       
-
+       /* 
+          Free all allocated surfaces 
+       */
        for(i = 0; i < psDevInfo->ulNumBuffers; i++)
        {
 #if defined(BC_DISCONTIG_BUFFERS)
@@ -477,7 +562,7 @@ BCE_ERROR BC_Example_Buffers_Destroy(void)
        }
        psDevInfo->ulNumBuffers = 0;
 
-       
+       /* Reset buffer info */
        psDevInfo->sBufferInfo.pixelformat        = PVRSRV_PIXEL_FORMAT_UNKNOWN;
        psDevInfo->sBufferInfo.ui32Width          = 0;
        psDevInfo->sBufferInfo.ui32Height         = 0;
@@ -486,11 +571,15 @@ BCE_ERROR BC_Example_Buffers_Destroy(void)
        psDevInfo->sBufferInfo.ui32Flags          = 0;
        psDevInfo->sBufferInfo.ui32BufferCount    = (IMG_UINT32)psDevInfo->ulNumBuffers;
 
-       
+       /* return success */
        return (BCE_OK);
 }
 
 
+/* 
+ * This function does both registration and buffer allocation at
+ * boot time.
+ */
 BCE_ERROR  BC_Example_Init(void)
 {
        BCE_ERROR eError;
@@ -510,6 +599,9 @@ BCE_ERROR  BC_Example_Init(void)
        return (BCE_OK);
 }
 
+/* 
+ *     Destroy buffers and unregister device.
+ */
 BCE_ERROR BC_Example_Deinit(void)
 {
        BCE_ERROR eError;
@@ -529,3 +621,6 @@ BCE_ERROR BC_Example_Deinit(void)
        return (BCE_OK);
 }
 
+/******************************************************************************
+ End of file (bufferclass_example.c)
+******************************************************************************/
index 572c3d7..4cdeb39 100644 (file)
@@ -1,32 +1,47 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          bufferclass_example kernel driver structures and prototypes
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __BC_EXAMPLE_H__
 #define __BC_EXAMPLE_H__
 
+/* IMG services headers */
 #include "img_defs.h"
 #include "servicesext.h"
 #include "kernelbuffer.h"
@@ -38,6 +53,9 @@ extern "C" {
 #define BC_EXAMPLE_NUM_BUFFERS  3
 
 #define NV12 1
+//#define YV12 1
+//#define YUV422 1
+
 #ifdef NV12
 
 #define BC_EXAMPLE_WIDTH        (320)
@@ -46,12 +64,12 @@ extern "C" {
 #define BC_EXAMPLE_PIXELFORMAT (PVRSRV_PIXEL_FORMAT_NV12)
 
 #else
-#ifdef I420
+#ifdef YV12
 
 #define BC_EXAMPLE_WIDTH        (320)
 #define BC_EXAMPLE_HEIGHT       (160)
 #define BC_EXAMPLE_STRIDE       (320)
-#define BC_EXAMPLE_PIXELFORMAT (PVRSRV_PIXEL_FORMAT_I420)
+#define BC_EXAMPLE_PIXELFORMAT (PVRSRV_PIXEL_FORMAT_YV12)
 
 #else
 #ifdef YUV422
@@ -82,13 +100,14 @@ typedef enum tag_bce_bool
        BCE_TRUE  = 1,
 } BCE_BOOL, *BCE_PBOOL;
 
+/* BC_NOHW buffer structure */
 typedef struct BC_EXAMPLE_BUFFER_TAG
 {
        unsigned long           ulSize;
        BCE_HANDLE              hMemHandle;
 
-       
-       
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
 #if defined(BC_DISCONTIG_BUFFERS)
        IMG_SYS_PHYADDR                         *psSysAddr;
 #else
@@ -102,36 +121,42 @@ typedef struct BC_EXAMPLE_BUFFER_TAG
 } BC_EXAMPLE_BUFFER;
 
 
+/* kernel device information structure */
 typedef struct BC_EXAMPLE_DEVINFO_TAG
 {
        unsigned long           ulDeviceID;
 
        BC_EXAMPLE_BUFFER       *psSystemBuffer;
 
-       
+       /* number of supported buffers */
        unsigned long           ulNumBuffers;
 
-       
+       /* jump table into PVR services */
        PVRSRV_BC_BUFFER2SRV_KMJTABLE sPVRJTable;
 
-       
+       /* jump table into BC */
        PVRSRV_BC_SRV2BUFFER_KMJTABLE sBCJTable;
 
-       
-
-
+       /*
+               handle for connection to kernel services
+               - OS specific - may not be required
+       */
        BCE_HANDLE              hPVRServices;
 
-       
+       /* ref count */
        unsigned long           ulRefCount;
 
-       
-       
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
        BUFFER_INFO             sBufferInfo;
 
 }  BC_EXAMPLE_DEVINFO;
 
 
+/*!
+ *****************************************************************************
+ * Error values
+ *****************************************************************************/
 typedef enum _BCE_ERROR_
 {
        BCE_OK                             =  0,
@@ -162,6 +187,7 @@ BCE_ERROR BC_Example_Buffers_Destroy(void);
 BCE_ERROR BC_Example_Init(void);
 BCE_ERROR BC_Example_Deinit(void);
 
+/* OS Specific APIs */
 BCE_ERROR BCOpenPVRServices(BCE_HANDLE *phPVRServices);
 BCE_ERROR BCClosePVRServices(BCE_HANDLE hPVRServices);
 
@@ -204,5 +230,9 @@ BC_EXAMPLE_DEVINFO * GetAnchorPtr(void);
 }
 #endif
 
-#endif 
+#endif /* __BC_EXAMPLE_H__ */
+
+/******************************************************************************
+ End of file (bufferclass_example.h)
+******************************************************************************/
 
index 6a855d2..90d25c8 100644 (file)
@@ -1,28 +1,70 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          bufferclass example linux specific implementations
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with 3rd Party display hardware.  It is NOT a specification for
+ a display controller driver, rather a specification to extend the API for a
+ pre-existing driver for the display hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying display hardware, allowing
+ the client drivers to indirectly control the display hardware and access its
+ associated memory.
+ Functions of the API include
+ - query primary surface attributes (width, height, stride, pixel format, CPU
+     physical and virtual address)
+ - swap/flip chain creation and subsequent query of surface attributes
+ - asynchronous display surface flipping, taking account of asynchronous read
+ (flip) and write (render) operations to the display surface
+
+ Note: having queried surface attributes the client drivers are able to map the
+ display memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the display surface handle.
+
+ This code is intended to be an example of how a pre-existing display driver may
+ be extended to support the 3rd Party Display interface to POWERVR Services
+ - IMG is not providing a display driver implementation.
+ **************************************************************************/
 
 #include <linux/version.h>
 #include <linux/kernel.h>
@@ -77,9 +119,15 @@ static DEFINE_MUTEX(sBCExampleBridgeMutex);
 #endif
 
 #if defined(LDM_PLATFORM) || defined(LDM_PCI)
+/*
+ * Device class used for /sys entries (and udev device node creation)
+ */
 static struct class *psPvrClass;
 #endif
 
+/*
+ * This is the major number we use for all nodes in /dev.
+ */
 static int AssignedMajorNumber;
 
 static struct file_operations bufferclass_example_fops = {
@@ -94,22 +142,46 @@ static struct file_operations bufferclass_example_fops = {
 #define unref__ __attribute__ ((unused))
 
 #if defined(LMA)
-#define PVR_BUFFERCLASS_MEMOFFSET (220 * 1024 * 1024) 
-#define PVR_BUFFERCLASS_MEMSIZE          (4 * 1024 * 1024)       
+#define PVR_BUFFERCLASS_MEMOFFSET (220 * 1024 * 1024) /* Must be after services localmem region */
+#define PVR_BUFFERCLASS_MEMSIZE          (4 * 1024 * 1024)       /* Must be before displayclass localmem region */
 
 unsigned long g_ulMemBase = 0;
 unsigned long g_ulMemCurrent = 0;
 
+/* PVR device vendor ID */
 #define VENDOR_ID_PVR               0x1010
 #define DEVICE_ID_PVR               0x1CF1
 
 #define DEVICE_ID1_PVR              0x1CF2
 
 
+/* PDP mem (including HP mapping) on base register 2 */
 #define PVR_MEM_PCI_BASENUM         2
 #endif
 
 
+/*****************************************************************************
+ Function Name:        BC_Example_ModInit
+ Description  :        Insert the driver into the kernel.
+
+                               The device major number is allocated by the kernel dynamically
+                               if AssignedMajorNumber is zero on entry.  This means that the
+                               device node (nominally /dev/bc_example) may need to be re-made if
+                               the kernel varies the major number it assigns.  The number
+                               does seem to stay constant between runs, but I don't think
+                               this is guaranteed. The node is made as root on the shell
+                               with:
+
+                                               mknod /dev/bc_example c ? 0
+
+                               where ? is the major number reported by the printk() - look
+                               at the boot log using `dmesg' to see this).
+
+                               __init places the function in a special memory section that
+                               the kernel frees once the function has been run.  Refer also
+                               to module_init() macro call below.
+
+*****************************************************************************/
 static int __init BC_Example_ModInit(void)
 {
 #if defined(LDM_PLATFORM) || defined(LDM_PCI)
@@ -125,7 +197,7 @@ static int __init BC_Example_ModInit(void)
        psPCIDev = pci_get_device(VENDOR_ID_PVR, DEVICE_ID_PVR, NULL);
        if (psPCIDev == NULL)
        {
-               
+               /* Try an alternative PCI ID */
                psPCIDev = pci_get_device(VENDOR_ID_PVR, DEVICE_ID1_PVR, NULL);
        }
 
@@ -157,7 +229,10 @@ static int __init BC_Example_ModInit(void)
 #endif
 
 #if defined(LDM_PLATFORM) || defined(LDM_PCI)
-       
+       /*
+        * This code (using GPL symbols) facilitates automatic device
+        * node creation on platforms with udev (or similar).
+        */
        psPvrClass = class_create(THIS_MODULE, "bc_example");
 
        if (IS_ERR(psPvrClass))
@@ -169,17 +244,20 @@ static int __init BC_Example_ModInit(void)
        psDev = device_create(psPvrClass, NULL, MKDEV(AssignedMajorNumber, 0),
 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26))
                                                  NULL,
-#endif 
+#endif /* (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26)) */
                                                  DEVNAME);
        if (IS_ERR(psDev))
        {
                printk(KERN_ERR DRVNAME ": BC_Example_ModInit: unable to create device (%ld)", PTR_ERR(psDev));
                goto ExitDestroyClass;
        }
-#endif 
+#endif /* defined(LDM_PLATFORM) || defined(LDM_PCI) */
 
 #if defined(LMA)
-       
+       /*
+        * We don't do a pci_request_region for  PVR_MEM_PCI_BASENUM, 
+        * we assume the SGX driver has done this already.
+        */
        g_ulMemBase =  pci_resource_start(psPCIDev, PVR_MEM_PCI_BASENUM) + PVR_BUFFERCLASS_MEMOFFSET;
 #endif
 
@@ -190,7 +268,11 @@ static int __init BC_Example_ModInit(void)
        }
 
 #if defined(LMA)
-       
+       /*
+        * To prevent possible problems with system suspend/resume, we don't
+        * keep the device enabled, but rely on the fact that the SGX driver
+        * will have done a pci_enable_device.
+        */
        pci_disable_device(psPCIDev);
 #endif
 
@@ -208,8 +290,17 @@ ExitDisable:
 ExitError:
 #endif
        return -EBUSY;
-} 
+} /*BC_Example_ModInit*/
+
+/*****************************************************************************
+ Function Name:        BC_Example_ModInit
+ Description  :        Remove the driver from the kernel.
 
+                               __exit places the function in a special memory section that
+                               the kernel frees once the function has been run.  Refer also
+                               to module_exit() macro call below.
+
+*****************************************************************************/
 static void __exit BC_Example_ModCleanup(void)
 {
 #if defined(LDM_PLATFORM) || defined(LDM_PCI)
@@ -224,7 +315,7 @@ static void __exit BC_Example_ModCleanup(void)
                printk (KERN_ERR DRVNAME ": BC_Example_ModCleanup: can't deinit device\n");
        }
 
-} 
+} /*BC_Example_ModCleanup*/
 
 
 void *BCAllocKernelMem(unsigned long ulSize)
@@ -288,7 +379,7 @@ void BCFreeDiscontigMemory(unsigned long ulSize,
 
        vfree(LinAddr);
 }
-#else  
+#else  /* defined(BC_DISCONTIG_BUFFERS) */
 
 BCE_ERROR BCAllocContigMemory(unsigned long ulSize,
                               BCE_HANDLE unref__ *phMemHandle,
@@ -298,7 +389,7 @@ BCE_ERROR BCAllocContigMemory(unsigned long ulSize,
 #if defined(LMA)
        void *pvLinAddr;
        
-       
+       /* Only allowed a certain amount of memory for bufferclass buffers */
        if(g_ulMemCurrent + ulSize >= PVR_BUFFERCLASS_MEMSIZE)
        {
                return (BCE_ERROR_OUT_OF_MEMORY);
@@ -311,12 +402,12 @@ BCE_ERROR BCAllocContigMemory(unsigned long ulSize,
                pPhysAddr->uiAddr = g_ulMemBase + g_ulMemCurrent;
                *pLinAddr = pvLinAddr;  
 
-               
+               /* Not a real allocator; just increment the current address */
                g_ulMemCurrent += ulSize;
                return (BCE_OK);
        }
        return (BCE_ERROR_OUT_OF_MEMORY);
-#else  
+#else  /* defined(LMA) */
 #if defined(BCE_USE_SET_MEMORY)
        void *pvLinAddr;
        unsigned long ulAlignedSize = PAGE_ALIGN(ulSize);
@@ -337,7 +428,7 @@ BCE_ERROR BCAllocContigMemory(unsigned long ulSize,
        *pLinAddr = pvLinAddr;
 
        return (BCE_OK);
-#else  
+#else  /* BCE_USE_SET_MEMORY */
        dma_addr_t dma;
        void *pvLinAddr;
 
@@ -351,8 +442,8 @@ BCE_ERROR BCAllocContigMemory(unsigned long ulSize,
        *pLinAddr = pvLinAddr;
 
        return (BCE_OK);
-#endif 
-#endif 
+#endif /* BCE_USE_SET_MEMORY */
+#endif /* defined(LMA) */
 }
 
 void BCFreeContigMemory(unsigned long ulSize,
@@ -363,7 +454,7 @@ void BCFreeContigMemory(unsigned long ulSize,
 #if defined(LMA)
        g_ulMemCurrent -= ulSize;
        iounmap(LinAddr);
-#else  
+#else  /* defined(LMA) */
 #if defined(BCE_USE_SET_MEMORY)
        unsigned long ulAlignedSize = PAGE_ALIGN(ulSize);
        int iError;
@@ -375,34 +466,50 @@ void BCFreeContigMemory(unsigned long ulSize,
                printk(KERN_ERR DRVNAME ": BCFreeContigMemory:  set_memory_wb failed (%d)\n", iError);
        }
        kfree(LinAddr);
-#else  
+#else  /* BCE_USE_SET_MEMORY */
        dma_free_coherent(NULL, ulSize, LinAddr, (dma_addr_t)PhysAddr.uiAddr);
-#endif 
-#endif 
+#endif /* BCE_USE_SET_MEMORY */
+#endif /* defined(LMA) */
 }
-#endif 
-
+#endif /* defined(BC_DISCONTIG_BUFFERS) */
+
+/**************************************************************************
+       FUNCTION:   CpuPAddrToSysPAddrBC
+       PURPOSE:    Compute a system physical address from a cpu physical
+                   address.
+       PARAMETERS:     In:  cpu_paddr - cpu physical address.
+       RETURNS:        system physical address.
+ **************************************************************************/
 IMG_SYS_PHYADDR CpuPAddrToSysPAddrBC(IMG_CPU_PHYADDR cpu_paddr)
 {
        IMG_SYS_PHYADDR sys_paddr;
        
-       
+       /* This would only be an inequality if the CPU's MMU did not point to sys address 0, 
+          ie. multi CPU system */
        sys_paddr.uiAddr = cpu_paddr.uiAddr;
        return sys_paddr;
 }
 
+/**************************************************************************
+       FUNCTION:   SysPAddrToCpuPAddrBC
+       PURPOSE:    Compute a cpu physical address
+                   from a system physical address.
+       PARAMETERS:     In:  cpu_paddr - system physical address.
+       RETURNS:        cpu physical address.
+ **************************************************************************/
 IMG_CPU_PHYADDR SysPAddrToCpuPAddrBC(IMG_SYS_PHYADDR sys_paddr)
 {
        
        IMG_CPU_PHYADDR cpu_paddr;
-       
+       /* This would only be an inequality if the CPU's MMU did not point to sys address 0, 
+          ie. multi CPU system */
        cpu_paddr.uiAddr = sys_paddr.uiAddr;
        return cpu_paddr;
 }
 
 BCE_ERROR BCOpenPVRServices (BCE_HANDLE *phPVRServices)
 {
-       
+       /* Nothing to do - we have already checked services module insertion */
        *phPVRServices = 0;
        return (BCE_OK);
 }
@@ -410,7 +517,7 @@ BCE_ERROR BCOpenPVRServices (BCE_HANDLE *phPVRServices)
 
 BCE_ERROR BCClosePVRServices (BCE_HANDLE unref__ hPVRServices)
 {
-       
+       /* Nothing to do */
        return (BCE_OK);
 }
 
@@ -421,7 +528,7 @@ BCE_ERROR BCGetLibFuncAddr (BCE_HANDLE unref__ hExtDrv, char *szFunctionName, PF
                return (BCE_ERROR_INVALID_PARAMS);
        }
 
-       
+       /* Nothing to do - should be exported from pvrsrv.ko */
        *ppfnFuncTable = PVRGetBufferClassJTable;
 
        return (BCE_OK);
@@ -492,6 +599,12 @@ static long BC_Example_Bridge_Unlocked(struct file *file, unsigned int cmd, unsi
 }
 #endif
 
+/*
+ These macro calls define the initialisation and removal functions of the
+ driver.  Although they are prefixed `module_', they apply when compiling
+ statically as well; in both cases they define the function the kernel will
+ run to start/stop the driver.
+*/
 module_init(BC_Example_ModInit);
 module_exit(BC_Example_ModCleanup);
 
index b663608..65d7860 100644 (file)
@@ -1,29 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          bufferclass_example kernel driver interface
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __BC_EXAMPLE_LINUX_H__
 #define __BC_EXAMPLE_LINUX_H__
 
@@ -36,6 +50,7 @@ typedef struct BC_Example_ioctl_package_TAG
 
 }BC_Example_ioctl_package;
 
+/*!< Nov 2006: according to ioctl-number.txt 'g' wasn't in use. */
 #define BC_EXAMPLE_IOC_GID      'g'
 
 #define BC_EXAMPLE_IOWR(INDEX)  _IOWR(BC_EXAMPLE_IOC_GID, INDEX, BC_Example_ioctl_package)
@@ -44,5 +59,9 @@ typedef struct BC_Example_ioctl_package_TAG
 #define BC_Example_ioctl_get_buffer_count      BC_EXAMPLE_IOWR(1)
 #define BC_Example_ioctl_reconfigure_buffer BC_EXAMPLE_IOWR(2)
 
-#endif 
+#endif /* __BC_EXAMPLE_H__ */
+
+/******************************************************************************
+ End of file (bufferclass_example.h)
+******************************************************************************/
 
index 3a02eb9..d9dbfde 100644 (file)
@@ -1,28 +1,70 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Bufferclass example private functions.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with 3rd Party display hardware.  It is NOT a specification for
+ a display controller driver, rather a specification to extend the API for a
+ pre-existing driver for the display hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying display hardware, allowing
+ the client drivers to indirectly control the display hardware and access its
+ associated memory.
+ Functions of the API include
+ - query primary surface attributes (width, height, stride, pixel format, CPU
+     physical and virtual address)
+ - swap/flip chain creation and subsequent query of surface attributes
+ - asynchronous display surface flipping, taking account of asynchronous read
+ (flip) and write (render) operations to the display surface
+
+ Note: having queried surface attributes the client drivers are able to map the
+ display memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the display surface handle.
+
+ This code is intended to be an example of how a pre-existing display driver may
+ be extended to support the 3rd Party Display interface to POWERVR Services
+ - IMG is not providing a display driver implementation.
+ **************************************************************************/
 
 #include "bufferclass_example.h"
 #include "bufferclass_example_private.h"
@@ -61,7 +103,7 @@ static void FillNV12Image(void *pvDest, int width, int height, int bytestride)
                        u = (j<(height/2))? ((i<(width/2))? 0xFF:0x33) : ((i<(width/2))? 0x33:0xAA);
                        v = (j<(height/2))? ((i<(width/2))? 0xAC:0x0) : ((i<(width/2))? 0x03:0xEE);
 
-                       
+                       /* Byte order is VU */
                        pui16uv[count++] = (v << 8) | u;
 
                }
@@ -70,7 +112,7 @@ static void FillNV12Image(void *pvDest, int width, int height, int bytestride)
        iPhase++;
 }
 
-static void FillI420Image(void *pvDest, int width, int height, int bytestride)
+static void FillYV12Image(void *pvDest, int width, int height, int bytestride)
 {
        static int iPhase = 0;
        int             i, j;
@@ -96,28 +138,28 @@ static void FillI420Image(void *pvDest, int width, int height, int bytestride)
 
        for(j=0;j<height;j+=2)
        {
-               pui8u = (unsigned char *)pvDest + (height * bytestride) + ((j / 2) * uvplanestride);
+               pui8v = (unsigned char *)pvDest + (height * bytestride) + ((j / 2) * uvplanestride);
                count = 0;
 
                for(i=0;i<width;i+=2)
                {
-                       u = (j<(height/2))? ((i<(width/2))? 0xFF:0x33) : ((i<(width/2))? 0x33:0xAA);
-
-                       pui8u[count++] = u;
+                       v = (j<(height/2))? ((i<(width/2))? 0xAC:0x0) : ((i<(width/2))? 0x03:0xEE);
 
+                       pui8v[count++] = v;
                }
        }
 
        for(j=0;j<height;j+=2)
        {
-               pui8v = (unsigned char *)pvDest + (height * bytestride) + (uvplaneheight * uvplanestride) + (j / 2) * uvplanestride;
+               pui8u = (unsigned char *)pvDest + (height * bytestride) + (uvplaneheight * uvplanestride) + (j / 2) * uvplanestride;
                count = 0;
 
                for(i=0;i<width;i+=2)
                {
-                       v = (j<(height/2))? ((i<(width/2))? 0xAC:0x0) : ((i<(width/2))? 0x03:0xEE);
+                       u = (j<(height/2))? ((i<(width/2))? 0xFF:0x33) : ((i<(width/2))? 0x33:0xAA);
+
+                       pui8u[count++] = u;
 
-                       pui8v[count++] = v;
                }
        }
 
@@ -177,7 +219,7 @@ static void FillRGB565Image(void *pvDest, int width, int height, int bytestride)
        unsigned short *pui16Addr = (unsigned short *)pvDest;
        unsigned long   Colour32;
        unsigned short  Colour16;
-       static unsigned char Colour8 = 0;
+       static unsigned char Colour8 = 0;//debug colour
        
        Colour16 = (Colour8>>3) | ((Colour8>>2)<<5) | ((Colour8>>3)<<11);
        Colour32 = Colour16 | Colour16 << 16;
@@ -208,11 +250,25 @@ static void FillRGB565Image(void *pvDest, int width, int height, int bytestride)
                pui32Addr[i] = 0x001F001FUL;
        }
 
-       
+       /* advance the colour */
        Colour8 = (Colour8 + 1) % MIN(height - 1, 0xFFU);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     FillBuffer
+ @Description 
+ Fills pixels into a buffer specified by index
+ @Input        ui32BufferIndex - buffer index
+ @Return       0 - success, -1 - failure
+
+******************************************************************************/
 int FillBuffer(unsigned int uiBufferIndex)
 {
        BC_EXAMPLE_DEVINFO  *psDevInfo = GetAnchorPtr();
@@ -220,27 +276,27 @@ int FillBuffer(unsigned int uiBufferIndex)
        BUFFER_INFO         *psBufferInfo;
        PVRSRV_SYNC_DATA    *psSyncData;
 
-       
+       /* check DevInfo has been setup */
        if(psDevInfo == NULL)
        {
-               return -1;
+               return -1;/* failure */
        }
 
        psBuffer = &psDevInfo->psSystemBuffer[uiBufferIndex];
        psBufferInfo = &psDevInfo->sBufferInfo;
 
-       
+       /* This may be NULL, as it is only registered once texture streaming starts. */
        psSyncData = psBuffer->psSyncData;
 
        if(psSyncData)
        {
-               
+               /* ensure all reads have flushed on the buffer */
                if(psSyncData->ui32ReadOpsPending != psSyncData->ui32ReadOpsComplete)
                {
-                       return -1;
+                       return -1;/* failure */
                }
 
-               
+               /* take a write-lock on the new buffer to capture to */
                psSyncData->ui32WriteOpsPending++;
        }
 
@@ -275,9 +331,9 @@ int FillBuffer(unsigned int uiBufferIndex)
                                                        psBufferInfo->ui32ByteStride);
                        break;
                }
-               case PVRSRV_PIXEL_FORMAT_I420:
+               case PVRSRV_PIXEL_FORMAT_YV12:
                {
-                       FillI420Image(psBuffer->sCPUVAddr, 
+                       FillYV12Image(psBuffer->sCPUVAddr, 
                                                        psBufferInfo->ui32Width, 
                                                        psBufferInfo->ui32Height, 
                                                        psBufferInfo->ui32ByteStride);
@@ -285,7 +341,7 @@ int FillBuffer(unsigned int uiBufferIndex)
                }
        }
 
-       
+       /* unlock the buffer, signalling the writes are complete */
        if(psSyncData)
        {
                psSyncData->ui32WriteOpsComplete++;
@@ -300,17 +356,31 @@ int FillBuffer(unsigned int uiBufferIndex)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     GetBufferCount
+ @Description 
+ returns buffer count
+ @Output       pulBufferCount - buffer count
+ @Return       0 - success, -1 - failure
+
+******************************************************************************/
 int GetBufferCount(unsigned int *puiBufferCount)
 {
        BC_EXAMPLE_DEVINFO *psDevInfo = GetAnchorPtr();
 
-       
+       /* check DevInfo has been setup */
        if(psDevInfo == IMG_NULL)
        {
-               return -1;
+               return -1;/* failure */
        }
 
-       
+       /* return buffer count */
        *puiBufferCount = (unsigned int)psDevInfo->sBufferInfo.ui32BufferCount;
 
        return 0;
@@ -318,11 +388,24 @@ int GetBufferCount(unsigned int *puiBufferCount)
 
 
 
+/******************************************************************************
+
+ @Function  ReconfigureBuffer
+
+ @Description
+
+ returns whether reconfiguration succeeds or not 
+
+ @Output   uiSucceed : 1 - succeeded, 0 - failed 
+
+ @Return   0 - success, -1 - failure
+
+******************************************************************************/
 int ReconfigureBuffer(unsigned int *uiSucceed)
 {
        BCE_ERROR eError;
  
-       
+       /* Destroy the shared buffers of the current buffer class device */
        eError = BC_Example_Buffers_Destroy();
 
        if (eError != BCE_OK)
@@ -331,10 +414,10 @@ int ReconfigureBuffer(unsigned int *uiSucceed)
                return -1;
        }
 
-       
+       /* No need to un-register and then re-register the device with services module srvkm */
 
 
-       
+       /* Recreate shared buffers with reconfigured parameters */
        eError = BC_Example_Buffers_Create();
 
        if (eError != BCE_OK)
@@ -343,7 +426,7 @@ int ReconfigureBuffer(unsigned int *uiSucceed)
                return -1;
        }
 
-       
+       /* return uiSucceed as succeeded 1 */
        *uiSucceed = 1;
        return 0;
 }
index 94515bc..8d95e2b 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Bufferclass example internal interfaces.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _BUFFERCLASS_EXAMPLE_PRIVATE_H_
 #define _BUFFERCLASS_EXAMPLE_PRIVATE_H_
@@ -31,4 +46,4 @@ int FillBuffer(unsigned int uiBufferIndex);
 int GetBufferCount(unsigned int *puiBufferCount);
 int ReconfigureBuffer(unsigned int *uiSucceed);
 
-#endif 
+#endif /* _BUFFERCLASS_EXAMPLE_PRIVATE_H_ */
index 04f5c38..d515885 100644 (file)
@@ -47,7 +47,7 @@
 
 #define DEVNAME             "bccat"
 #define DRVNAME             DEVNAME
-#define DEVICE_COUNT        1
+#define DEVICE_COUNT        10
 #define BC_EXAMPLE_NUM_BUFFERS  3
 #define BUFFERCLASS_DEVICE_NAME "Example Bufferclass Device (SW)"
 
@@ -324,6 +324,15 @@ static int BC_CreateBuffers(int id, bc_buf_params_t *p)
         return -EINVAL;
 
     switch (p->fourcc) {
+    case BC_PIX_FMT_YV12:
+        pixel_fmt = PVRSRV_PIXEL_FORMAT_YV12;
+        stride = p->width;
+        break;
+    case BC_PIX_FMT_I420:
+        pixel_fmt = PVRSRV_PIXEL_FORMAT_I420;
+        stride = p->width;
+        break;
+
     case BC_PIX_FMT_NV12:
         pixel_fmt = PVRSRV_PIXEL_FORMAT_NV12;
         stride = p->width;
@@ -381,6 +390,12 @@ static int BC_CreateBuffers(int id, bc_buf_params_t *p)
     if (pixel_fmt == PVRSRV_PIXEL_FORMAT_NV12)
         ulSize += (stride >> 1) * (p->height >> 1) << 1;
 
+    if ((pixel_fmt == PVRSRV_PIXEL_FORMAT_I420) || (pixel_fmt == PVRSRV_PIXEL_FORMAT_YV12) )
+    {
+        ulSize += (stride >> 1) * (p->height >> 1);
+        ulSize += (stride >> 1) * (p->height >> 1);
+    }
+
     for (i=0; i < p->count; i++) {
         if (psDevInfo->buf_type == BC_MEMORY_MMAP) {
 
@@ -662,7 +677,8 @@ static int __init bc_cat_init(void)
 #ifdef PLAT_TI8168
      width_align = 8;
 #else
-     width_align = cpu_is_omap3530() && ( omap_rev() < OMAP3430_REV_ES3_0 ) ? 32 : 8; 
+     width_align = 8;
+     //width_align = cpu_is_omap3530() && ( omap_rev() < OMAP3430_REV_ES3_0 ) ? 32 : 8; 
 #endif   
  
     major = register_chrdev(0, DEVNAME, &bc_cat_fops);
index 0b436ee..7d45649 100644 (file)
@@ -33,6 +33,8 @@
 #define BC_FOURCC(a,b,c,d) \
     ((unsigned long) ((a) | (b)<<8 | (c)<<16 | (d)<<24))
 
+#define BC_PIX_FMT_I420     BC_FOURCC('I', '4', '2', '0') /*YUV 4:2:0*/
+#define BC_PIX_FMT_YV12     BC_FOURCC('Y', 'V', '1', '2') /*YUV 4:2:0*/
 #define BC_PIX_FMT_NV12     BC_FOURCC('N', 'V', '1', '2') /*YUV 4:2:0*/
 #define BC_PIX_FMT_UYVY     BC_FOURCC('U', 'Y', 'V', 'Y') /*YUV 4:2:2*/
 #define BC_PIX_FMT_YUYV     BC_FOURCC('Y', 'U', 'Y', 'V') /*YUV 4:2:2*/
index a48c8dc..addbfc2 100644 (file)
@@ -1,29 +1,46 @@
-/**********************************************************************
- *
- * Copyright(c) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OMAP Linux display driver shared DRM structures
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    OMAP Linux display driver DRM structures shared between
+                kernel and user space.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
 #ifndef __3RDPARTY_DC_DRM_SHARED_H__
 #define __3RDPARTY_DC_DRM_SHARED_H__
 #if defined(SUPPORT_DRI_DRM)
@@ -40,6 +57,9 @@
 #define        PVR_DRM_DISP_ARG_DEV            1
 #define        PVR_DRM_DISP_NUM_ARGS           2
 
-#endif 
-#endif 
+#endif /* defined(SUPPORT_DRI_DRM) */
+#endif /* __3RDPARTY_DC_DRM_SHARED_H__ */
 
+/******************************************************************************
+ End of file (3rdparty_dc_drm_shared.h)
+******************************************************************************/
diff --git a/services4/3rdparty/dc_omapfb3_linux/Kbuild.mk b/services4/3rdparty/dc_omapfb3_linux/Kbuild.mk
new file mode 100644 (file)
index 0000000..eca9351
--- /dev/null
@@ -0,0 +1,49 @@
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
+# 
+# The contents of this file are subject to the MIT license as set out below.
+# 
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+# 
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+# 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
+# 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#   
+### ###########################################################################
+
+ccflags-y += \
+       -I$(TOP)/services4/3rdparty/dc_omapfb3_linux \
+       -I$(KERNELDIR)/drivers/video/omap2 \
+       -I$(KERNELDIR)/arch/arm/plat-omap/include
+
+omaplfb-y += \
+       services4/3rdparty/dc_omapfb3_linux/omaplfb_displayclass.o \
+       services4/3rdparty/dc_omapfb3_linux/omaplfb_linux.o
diff --git a/services4/3rdparty/dc_omapfb3_linux/Linux.mk b/services4/3rdparty/dc_omapfb3_linux/Linux.mk
new file mode 100644 (file)
index 0000000..7574073
--- /dev/null
@@ -0,0 +1,46 @@
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
+# 
+# The contents of this file are subject to the MIT license as set out below.
+# 
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+# 
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+# 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
+# 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#   
+### ###########################################################################
+
+modules := dc_omapfb3_linux
+
+dc_omapfb3_linux_type := kernel_module
+dc_omapfb3_linux_target := omaplfb.ko
+dc_omapfb3_linux_makefile := $(THIS_DIR)/Kbuild.mk
diff --git a/services4/3rdparty/dc_omapfb3_linux/kbuild/Makefile b/services4/3rdparty/dc_omapfb3_linux/kbuild/Makefile
deleted file mode 100644 (file)
index f52617a..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-#
-# Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
-# 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
-# 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
-# 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
-# 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
-# 
-#
-
-MODULE         = $(DISPLAY_CONTROLLER)
-
-INCLUDES =
-
-SOURCES        =
-
-SYM_VERS_DEPS = $(EURASIAROOT)/services4/srvkm/env/linux
-
-include $(EURASIAROOT)/services4/$(DISPLAY_CONTROLLER_DIR)/makefile.linux.common
-
-include $(EURASIAROOT)/eurasiacon/build/linux/kbuild/Makefile.kbuild_subdir_common
diff --git a/services4/3rdparty/dc_omapfb3_linux/makefile.linux.common b/services4/3rdparty/dc_omapfb3_linux/makefile.linux.common
deleted file mode 100644 (file)
index d5b4a30..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-#
-# Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
-# 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
-# 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
-# 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
-# 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
-# 
-#
-#
-
-ifeq ($(SUPPORT_DRI_DRM),1)
-DISPLAY_CONTROLLER_SOURCES_ROOT = $(KBUILDROOT)/$(DISPLAY_CONTROLLER_DIR)
-MODULE_CFLAGS += -DPVR_DISPLAY_CONTROLLER_DRM_IOCTL
-else
-DISPLAY_CONTROLLER_SOURCES_ROOT = ..
-endif
-
-INCLUDES +=    -I$(EURASIAROOT)/include4 \
-               -I$(EURASIAROOT)/services4/include \
-               -I$(EURASIAROOT)/services4/system/$(PVR_SYSTEM) \
-               -I$(EURASIAROOT)/services4/system/include \
-               -I$(KERNELDIR)/drivers/video/omap2 \
-               -I$(KERNELDIR)/arch/arm/plat-omap/include
-
-SOURCES        +=      $(DISPLAY_CONTROLLER_SOURCES_ROOT)/omaplfb_displayclass.c \
-                       $(DISPLAY_CONTROLLER_SOURCES_ROOT)/omaplfb_linux.c
index b77ee39..c69640d 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright(c) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          OMAP Linux display driver structures and prototypes
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
 #ifndef __OMAPLFB_H__
 #define __OMAPLFB_H__
 
 #include <linux/earlysuspend.h>
 #endif
 
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38))
+#define        OMAPLFB_CONSOLE_LOCK()          console_lock()
+#define        OMAPLFB_CONSOLE_UNLOCK()        console_unlock()
+#else
+#define        OMAPLFB_CONSOLE_LOCK()          acquire_console_sem()
+#define        OMAPLFB_CONSOLE_UNLOCK()        release_console_sem()
+#endif
+
 #define unref__ __attribute__ ((unused))
 
 typedef void *       OMAPLFB_HANDLE;
@@ -55,6 +78,7 @@ typedef       atomic_t        OMAPLFB_ATOMIC_BOOL;
 
 typedef atomic_t       OMAPLFB_ATOMIC_INT;
 
+/* OMAPLFB buffer structure */
 typedef struct OMAPLFB_BUFFER_TAG
 {
        struct OMAPLFB_BUFFER_TAG       *psNext;
@@ -62,11 +86,11 @@ typedef struct OMAPLFB_BUFFER_TAG
 
        struct work_struct sWork;
 
-       
+       /* Position of this buffer in the virtual framebuffer */
        unsigned long                   ulYOffset;
 
-       
-       
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
        IMG_SYS_PHYADDR                 sSysAddr;
        IMG_CPU_VIRTADDR                sCPUVAddr;
        PVRSRV_SYNC_DATA                *psSyncData;
@@ -75,27 +99,34 @@ typedef struct OMAPLFB_BUFFER_TAG
        unsigned long                   ulSwapInterval;
 } OMAPLFB_BUFFER;
 
+/* OMAPLFB swapchain structure */
 typedef struct OMAPLFB_SWAPCHAIN_TAG
 {
-       
+       /* Swap chain ID */
        unsigned int                    uiSwapChainID;
 
-       
+       /* number of buffers in swapchain */
        unsigned long                   ulBufferCount;
 
-       
+       /* list of buffers in the swapchain */
        OMAPLFB_BUFFER                  *psBuffer;
 
-       
+       /* Swap chain work queue */
        struct workqueue_struct         *psWorkQueue;
 
-       
+       /*
+        * Set if we didn't manage to wait for VSync on last swap,
+        * or if we think we need to wait for VSync on the next flip.
+        * The flag helps to avoid jitter when the screen is
+        * unblanked, by forcing an extended wait for VSync before
+        * attempting the next flip.
+        */
        OMAPLFB_BOOL                    bNotVSynced;
 
-       
+       /* Previous number of blank events */
        int                             iBlankEvents;
 
-       
+       /* Framebuffer Device ID for messages (e.g. printk) */
        unsigned int                    uiFBDevID;
 } OMAPLFB_SWAPCHAIN;
 
@@ -110,75 +141,83 @@ typedef struct OMAPLFB_FBINFO_TAG
        unsigned long       ulPhysicalWidthmm;
        unsigned long       ulPhysicalHeightmm;
 
-       
-       
-       IMG_SYS_PHYADDR     sSysAddr;
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
+       IMG_SYS_PHYADDR     sSysAddr;//system physical address
        IMG_CPU_VIRTADDR    sCPUVAddr;
 
-       
+       /* pixelformat of system/primary surface */
        PVRSRV_PIXEL_FORMAT ePixelFormat;
-}OMAPLFB_FBINFO;
 
+#if defined(CONFIG_DSSCOMP)
+       OMAPLFB_BOOL            bIs2D;
+       IMG_SYS_PHYADDR         *psPageList;
+       struct ion_handle       *psIONHandle;
+       IMG_UINT32                      uiBytesPerPixel;
+#endif
+} OMAPLFB_FBINFO;
+
+/* kernel device information structure */
 typedef struct OMAPLFB_DEVINFO_TAG
 {
-       
+       /* Framebuffer Device ID */
        unsigned int            uiFBDevID;
 
-       
+       /* PVR Device ID */
        unsigned int            uiPVRDevID;
 
-       
+       /* Swapchain create/destroy mutex */
        struct mutex            sCreateSwapChainMutex;
 
-       
+       /* system surface info */
        OMAPLFB_BUFFER          sSystemBuffer;
 
-       
+       /* jump table into PVR services */
        PVRSRV_DC_DISP2SRV_KMJTABLE     sPVRJTable;
        
-       
+       /* jump table into DC */
        PVRSRV_DC_SRV2DISP_KMJTABLE     sDCJTable;
 
-       
+       /* fb info structure */
        OMAPLFB_FBINFO          sFBInfo;
 
-       
+       /* Only one swapchain supported by this device so hang it here */
        OMAPLFB_SWAPCHAIN      *psSwapChain;
 
-       
+       /* Swap chain ID */
        unsigned int            uiSwapChainID;
 
-       
+       /* True if PVR Services is flushing its command queues */
        OMAPLFB_ATOMIC_BOOL     sFlushCommands;
 
-       
+       /* pointer to linux frame buffer information structure */
        struct fb_info         *psLINFBInfo;
 
-       
+       /* Linux Framebuffer event notification block */
        struct notifier_block   sLINNotifBlock;
 
-       
-       
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
 
-       
+       /* Address of the surface being displayed */
        IMG_DEV_VIRTADDR        sDisplayDevVAddr;
 
        DISPLAY_INFO            sDisplayInfo;
 
-       
+       /* Display format */
        DISPLAY_FORMAT          sDisplayFormat;
        
-       
+       /* Display dimensions */
        DISPLAY_DIMS            sDisplayDim;
 
-       
+       /* True if screen is blanked */
        OMAPLFB_ATOMIC_BOOL     sBlanked;
 
-       
+       /* Number of blank/unblank events */
        OMAPLFB_ATOMIC_INT      sBlankEvents;
 
 #ifdef CONFIG_HAS_EARLYSUSPEND
-       
+       /* Set by early suspend */
        OMAPLFB_ATOMIC_BOOL     sEarlySuspendFlag;
 
        struct early_suspend    sEarlySuspend;
@@ -192,6 +231,7 @@ typedef struct OMAPLFB_DEVINFO_TAG
 
 #define        OMAPLFB_PAGE_SIZE 4096
 
+/* DEBUG only printk */
 #ifdef DEBUG
 #define        DEBUG_PRINTK(x) printk x
 #else
@@ -203,6 +243,10 @@ typedef struct OMAPLFB_DEVINFO_TAG
 #define        DEVNAME DRVNAME
 #define        DRIVER_PREFIX DRVNAME
 
+/*!
+ *****************************************************************************
+ * Error values
+ *****************************************************************************/
 typedef enum _OMAPLFB_ERROR_
 {
        OMAPLFB_OK                             =  0,
@@ -232,6 +276,7 @@ typedef enum _OMAPLFB_UPDATE_MODE_
 OMAPLFB_ERROR OMAPLFBInit(void);
 OMAPLFB_ERROR OMAPLFBDeInit(void);
 
+/* OS Specific APIs */
 OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID);
 unsigned OMAPLFBMaxFBDevIDPlusOne(void);
 void *OMAPLFBAllocKernelMem(unsigned long ulSize);
@@ -265,5 +310,15 @@ void OMAPLFBAtomicIntSet(OMAPLFB_ATOMIC_INT *psAtomic, int iVal);
 int OMAPLFBAtomicIntRead(OMAPLFB_ATOMIC_INT *psAtomic);
 void OMAPLFBAtomicIntInc(OMAPLFB_ATOMIC_INT *psAtomic);
 
-#endif 
+#if defined(DEBUG)
+void OMAPLFBPrintInfo(OMAPLFB_DEVINFO *psDevInfo);
+#else
+#define        OMAPLFBPrintInfo(psDevInfo)
+#endif
+
+#endif /* __OMAPLFB_H__ */
+
+/******************************************************************************
+ End of file (omaplfb.h)
+******************************************************************************/
 
index 0f139ab..085b5a1 100644 (file)
@@ -1,28 +1,77 @@
-/**********************************************************************
- *
- * Copyright(c) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OMAP common display driver components
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with 3rd Party display hardware.  It is NOT a specification for
+ a display controller driver, rather a specification to extend the API for a
+ pre-existing driver for the display hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying display hardware, allowing
+ the client drivers to indirectly control the display hardware and access its
+ associated memory.
+ Functions of the API include
+ - query primary surface attributes (width, height, stride, pixel format, CPU
+     physical and virtual address)
+ - swap/flip chain creation and subsequent query of surface attributes
+ - asynchronous display surface flipping, taking account of asynchronous read
+ (flip) and write (render) operations to the display surface
+
+ Note: having queried surface attributes the client drivers are able to map the
+ display memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the display surface handle.
+
+ This code is intended to be an example of how a pre-existing display driver may
+ be extended to support the 3rd Party Display interface to POWERVR Services
+ - IMG is not providing a display driver implementation.
+ **************************************************************************/
+
+/*
+ * OMAP Linux 3rd party display driver.
+ * This is based on the Generic PVR Linux Framebuffer 3rd party display
+ * driver, with OMAP specific extensions to support flipping.
+ */
 
 #include <linux/version.h>
 #include <linux/kernel.h>
 #include <linux/string.h>
 #include <linux/notifier.h>
 
+/* IMG services headers */
 #include "img_defs.h"
 #include "servicesext.h"
 #include "kerneldisplay.h"
 #include "omaplfb.h"
 
+#if defined(CONFIG_DSSCOMP)
+
+#if !defined(CONFIG_ION_OMAP)
+#error CONFIG_DSSCOMP support requires CONFIG_ION_OMAP
+#endif
+
+#include <linux/ion.h>
+#include <linux/omap_ion.h>
+
+extern struct ion_client *gpsIONClient;
+
+#include <mach/tiler.h>
+#include <video/dsscomp.h>
+#include <plat/dsscomp.h>
+
+#endif /* defined(CONFIG_DSSCOMP) */
+
 #define OMAPLFB_COMMAND_COUNT          1
 
 #define        OMAPLFB_VSYNC_SETTLE_COUNT      5
 
 //#define      OMAPLFB_MAX_NUM_DEVICES         FB_MAX
-#define        OMAPLFB_MAX_NUM_DEVICES 1
-
+#define        OMAPLFB_MAX_NUM_DEVICES         1
 #if (OMAPLFB_MAX_NUM_DEVICES > FB_MAX)
 #error "OMAPLFB_MAX_NUM_DEVICES must not be greater than FB_MAX"
 #endif
 
 static OMAPLFB_DEVINFO *gapsDevInfo[OMAPLFB_MAX_NUM_DEVICES];
 
+/* Top level 'hook ptr' */
 static PFN_DC_GET_PVRJTABLE gpfnGetPVRJTable = NULL;
 
+/* Round x up to a multiple of y */
 static inline unsigned long RoundUpToMultiple(unsigned long x, unsigned long y)
 {
        unsigned long div = x / y;
@@ -60,6 +128,7 @@ static inline unsigned long RoundUpToMultiple(unsigned long x, unsigned long y)
        return (div + ((rem == 0) ? 0 : 1)) * y;
 }
 
+/* Greatest common divisor of x and y */
 static unsigned long GCD(unsigned long x, unsigned long y)
 {
        while (y != 0)
@@ -72,6 +141,7 @@ static unsigned long GCD(unsigned long x, unsigned long y)
        return x;
 }
 
+/* Least common multiple of x and y */
 static unsigned long LCM(unsigned long x, unsigned long y)
 {
        unsigned long gcd = GCD(x, y);
@@ -84,6 +154,7 @@ unsigned OMAPLFBMaxFBDevIDPlusOne(void)
        return OMAPLFB_MAX_NUM_DEVICES;
 }
 
+/* Returns DevInfo pointer for a given device */
 OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID)
 {
        WARN_ON(uiFBDevID >= OMAPLFBMaxFBDevIDPlusOne());
@@ -96,6 +167,7 @@ OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID)
        return gapsDevInfo[uiFBDevID];
 }
 
+/* Sets the DevInfo pointer for a given device */
 static inline void OMAPLFBSetDevInfoPtr(unsigned uiFBDevID, OMAPLFB_DEVINFO *psDevInfo)
 {
        WARN_ON(uiFBDevID >= OMAPLFB_MAX_NUM_DEVICES);
@@ -112,6 +184,7 @@ static inline OMAPLFB_BOOL SwapChainHasChanged(OMAPLFB_DEVINFO *psDevInfo, OMAPL
                (psDevInfo->uiSwapChainID != psSwapChain->uiSwapChainID);
 }
 
+/* Don't wait for vertical sync */
 static inline OMAPLFB_BOOL DontWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
 {
        OMAPLFB_BOOL bDontWait;
@@ -128,6 +201,10 @@ static inline OMAPLFB_BOOL DontWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
        return bDontWait;
 }
 
+/*
+ * SetDCState
+ * Called from services.
+ */
 static IMG_VOID SetDCState(IMG_HANDLE hDevice, IMG_UINT32 ui32State)
 {
        OMAPLFB_DEVINFO *psDevInfo = (OMAPLFB_DEVINFO *)hDevice;
@@ -140,11 +217,18 @@ static IMG_VOID SetDCState(IMG_HANDLE hDevice, IMG_UINT32 ui32State)
                case DC_STATE_NO_FLUSH_COMMANDS:
                        OMAPLFBAtomicBoolSet(&psDevInfo->sFlushCommands, OMAPLFB_FALSE);
                        break;
+               case DC_STATE_FORCE_SWAP_TO_SYSTEM:
+                       OMAPLFBFlip(psDevInfo, &psDevInfo->sSystemBuffer);
+                       break;
                default:
                        break;
        }
 }
 
+/*
+ * OpenDCDevice
+ * Called from services.
+ */
 static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                                  IMG_HANDLE *phDevice,
                                  PVRSRV_SYNC_DATA* psSystemBufferSyncData)
@@ -169,7 +253,7 @@ static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                return PVRSRV_ERROR_INVALID_DEVICE;
        }
 
-       
+       /* store the system surface sync data */
        psDevInfo->sSystemBuffer.psSyncData = psSystemBufferSyncData;
        
        eError = OMAPLFBUnblankDisplay(psDevInfo);
@@ -180,12 +264,16 @@ static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                return PVRSRV_ERROR_UNBLANK_DISPLAY_FAILED;
        }
 
-       
+       /* return handle to the devinfo */
        *phDevice = (IMG_HANDLE)psDevInfo;
        
        return PVRSRV_OK;
 }
 
+/*
+ * CloseDCDevice
+ * Called from services.
+ */
 static PVRSRV_ERROR CloseDCDevice(IMG_HANDLE hDevice)
 {
 #if defined(SUPPORT_DRI_DRM)
@@ -199,6 +287,10 @@ static PVRSRV_ERROR CloseDCDevice(IMG_HANDLE hDevice)
        return PVRSRV_OK;
 }
 
+/*
+ * EnumDCFormats
+ * Called from services.
+ */
 static PVRSRV_ERROR EnumDCFormats(IMG_HANDLE hDevice,
                                   IMG_UINT32 *pui32NumFormats,
                                   DISPLAY_FORMAT *psFormat)
@@ -222,6 +314,10 @@ static PVRSRV_ERROR EnumDCFormats(IMG_HANDLE hDevice,
        return PVRSRV_OK;
 }
 
+/*
+ * EnumDCDims
+ * Called from services.
+ */
 static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice, 
                                DISPLAY_FORMAT *psFormat,
                                IMG_UINT32 *pui32NumDims,
@@ -238,7 +334,7 @@ static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice,
 
        *pui32NumDims = 1;
 
-       
+       /* No need to look at psFormat; there is only one */
        if(psDim)
        {
                psDim[0] = psDevInfo->sDisplayDim;
@@ -248,6 +344,10 @@ static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice,
 }
 
 
+/*
+ * GetDCSystemBuffer
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCSystemBuffer(IMG_HANDLE hDevice, IMG_HANDLE *phBuffer)
 {
        OMAPLFB_DEVINFO *psDevInfo;
@@ -265,6 +365,10 @@ static PVRSRV_ERROR GetDCSystemBuffer(IMG_HANDLE hDevice, IMG_HANDLE *phBuffer)
 }
 
 
+/*
+ * GetDCInfo
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCInfo(IMG_HANDLE hDevice, DISPLAY_INFO *psDCInfo)
 {
        OMAPLFB_DEVINFO *psDevInfo;
@@ -281,6 +385,10 @@ static PVRSRV_ERROR GetDCInfo(IMG_HANDLE hDevice, DISPLAY_INFO *psDCInfo)
        return PVRSRV_OK;
 }
 
+/*
+ * GetDCBufferAddr
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
                                     IMG_HANDLE        hBuffer, 
                                     IMG_SYS_PHYADDR   **ppsSysAddr,
@@ -325,7 +433,11 @@ static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
 
        if (ppvCpuVAddr)
        {
+#if defined(CONFIG_DSSCOMP)
+               *ppvCpuVAddr = psDevInfo->sFBInfo.bIs2D ? NULL : psSystemBuffer->sCPUVAddr;
+#else
                *ppvCpuVAddr = psSystemBuffer->sCPUVAddr;
+#endif
        }
 
        if (phOSMapInfo)
@@ -335,12 +447,28 @@ static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
 
        if (pbIsContiguous)
        {
+#if defined(CONFIG_DSSCOMP)
+               *pbIsContiguous = !psDevInfo->sFBInfo.bIs2D;
+#else
                *pbIsContiguous = IMG_TRUE;
+#endif
        }
 
+#if defined(CONFIG_DSSCOMP)
+       if (psDevInfo->sFBInfo.bIs2D)
+       {
+               int i = (psSystemBuffer->sSysAddr.uiAddr - psDevInfo->sFBInfo.psPageList->uiAddr) >> PAGE_SHIFT;
+               *ppsSysAddr = psDevInfo->sFBInfo.psPageList + psDevInfo->sFBInfo.ulHeight * i;
+       }
+#endif
+
        return PVRSRV_OK;
 }
 
+/*
+ * CreateDCSwapChain
+ * Called from services.
+ */
 static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                                       IMG_UINT32 ui32Flags,
                                       DISPLAY_SURF_ATTRIBUTES *psDstSurfAttrib,
@@ -360,6 +488,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        UNREFERENCED_PARAMETER(ui32OEMFlags);
        
+       /* Check parameters */
        if(!hDevice
        || !psDstSurfAttrib
        || !psSrcSurfAttrib
@@ -371,7 +500,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        psDevInfo = (OMAPLFB_DEVINFO*)hDevice;
        
-       
+       /* Do we support swap chains? */
        if (psDevInfo->sDisplayInfo.ui32MaxSwapChains == 0)
        {
                return PVRSRV_ERROR_NOT_SUPPORTED;
@@ -379,14 +508,14 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        OMAPLFBCreateSwapChainLock(psDevInfo);
 
-       
+       /* The driver only supports a single swapchain */
        if(psDevInfo->psSwapChain != NULL)
        {
                eError = PVRSRV_ERROR_FLIP_CHAIN_EXISTS;
                goto ExitUnLock;
        }
        
-       
+       /* Check the buffer count */
        if(ui32BufferCount > psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers)
        {
                eError = PVRSRV_ERROR_TOOMANYBUFFERS;
@@ -399,16 +528,23 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                goto ExitUnLock;
        }
 
-       
+       /*
+        * We will allocate the swap chain buffers at the back of the frame
+        * buffer area.  This preserves the front portion, which may be being
+        * used by other Linux Framebuffer based applications.
+        */
        ui32BuffersToSkip = psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers - ui32BufferCount;
 
-       
+       /* 
+        *      Verify the DST/SRC attributes,
+        *      SRC/DST must match the current display mode config
+       */
        if(psDstSurfAttrib->pixelformat != psDevInfo->sDisplayFormat.pixelformat
        || psDstSurfAttrib->sDims.ui32ByteStride != psDevInfo->sDisplayDim.ui32ByteStride
        || psDstSurfAttrib->sDims.ui32Width != psDevInfo->sDisplayDim.ui32Width
        || psDstSurfAttrib->sDims.ui32Height != psDevInfo->sDisplayDim.ui32Height)
        {
-               
+               /* DST doesn't match the current mode */
                eError = PVRSRV_ERROR_INVALID_PARAMS;
                goto ExitUnLock;
        }               
@@ -418,12 +554,12 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
        || psDstSurfAttrib->sDims.ui32Width != psSrcSurfAttrib->sDims.ui32Width
        || psDstSurfAttrib->sDims.ui32Height != psSrcSurfAttrib->sDims.ui32Height)
        {
-               
+               /* DST doesn't match the SRC */
                eError = PVRSRV_ERROR_INVALID_PARAMS;
                goto ExitUnLock;
        }               
 
-       
+       /* check flags if implementation requires them */
        UNREFERENCED_PARAMETER(ui32Flags);
        
 #if defined(PVR_OMAPFB3_UPDATE_MODE)
@@ -432,7 +568,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set frame buffer update mode %d\n", __FUNCTION__, psDevInfo->uiFBDevID, PVR_OMAPFB3_UPDATE_MODE);
        }
 #endif
-       
+       /* create a swapchain structure */
        psSwapChain = (OMAPLFB_SWAPCHAIN*)OMAPLFBAllocKernelMem(sizeof(OMAPLFB_SWAPCHAIN));
        if(!psSwapChain)
        {
@@ -452,20 +588,27 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
        psSwapChain->bNotVSynced = OMAPLFB_TRUE;
        psSwapChain->uiFBDevID = psDevInfo->uiFBDevID;
 
-       
+       /* Link the buffers */
        for(i=0; i<ui32BufferCount-1; i++)
        {
                psBuffer[i].psNext = &psBuffer[i+1];
        }
-       
+       /* and link last to first */
        psBuffer[i].psNext = &psBuffer[0];
 
-       
+       /* Configure the swapchain buffers */
        for(i=0; i<ui32BufferCount; i++)
        {
                IMG_UINT32 ui32SwapBuffer = i + ui32BuffersToSkip;
                IMG_UINT32 ui32BufferOffset = ui32SwapBuffer * (IMG_UINT32)psDevInfo->sFBInfo.ulRoundedBufferSize;
 
+#if defined(CONFIG_DSSCOMP)
+               if (psDevInfo->sFBInfo.bIs2D)
+               {
+                       ui32BufferOffset = 0;
+               }
+#endif /* defined(CONFIG_DSSCOMP) */
+
                psBuffer[i].psSyncData = ppsSyncData[i];
 
                psBuffer[i].sSysAddr.uiAddr = psDevInfo->sFBInfo.sSysAddr.uiAddr + ui32BufferOffset;
@@ -473,6 +616,14 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                psBuffer[i].ulYOffset = ui32BufferOffset / psDevInfo->sFBInfo.ulByteStride;
                psBuffer[i].psDevInfo = psDevInfo;
 
+#if defined(CONFIG_DSSCOMP)
+               if (psDevInfo->sFBInfo.bIs2D)
+               {
+                       psBuffer[i].sSysAddr.uiAddr += ui32SwapBuffer *
+                               ALIGN((IMG_UINT32)psDevInfo->sFBInfo.ulWidth * psDevInfo->sFBInfo.uiBytesPerPixel, PAGE_SIZE);
+               }
+#endif /* defined(CONFIG_DSSCOMP) */
+
                OMAPLFBInitBufferForSwap(&psBuffer[i]);
        }
 
@@ -518,6 +669,10 @@ ExitUnLock:
        return eError;
 }
 
+/*
+ * DestroyDCSwapChain
+ * Called from services.
+ */
 static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
        IMG_HANDLE hSwapChain)
 {
@@ -525,7 +680,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
        OMAPLFB_SWAPCHAIN *psSwapChain;
        OMAPLFB_ERROR eError;
 
-       
+       /* Check parameters */
        if(!hDevice || !hSwapChain)
        {
                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -545,7 +700,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
                goto ExitUnLock;
        }
 
-       
+       /* The swap queue is flushed before being destroyed */
        OMAPLFBDestroySwapQueue(psSwapChain);
 
        eError = OMAPLFBDisableLFBEventNotification(psDevInfo);
@@ -554,7 +709,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
                printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't disable framebuffer event notification\n", __FUNCTION__, psDevInfo->uiFBDevID);
        }
 
-       
+       /* Free resources */
        OMAPLFBFreeKernelMem(psSwapChain->psBuffer);
        OMAPLFBFreeKernelMem(psSwapChain);
 
@@ -571,6 +726,10 @@ ExitUnLock:
        return eError;
 }
 
+/*
+ * SetDCDstRect
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCDstRect(IMG_HANDLE hDevice,
        IMG_HANDLE hSwapChain,
        IMG_RECT *psRect)
@@ -579,11 +738,15 @@ static PVRSRV_ERROR SetDCDstRect(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(psRect);
 
-       
+       /* Only full display swapchains on this device */
        
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCSrcRect
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCSrcRect(IMG_HANDLE hDevice,
                                  IMG_HANDLE hSwapChain,
                                  IMG_RECT *psRect)
@@ -592,11 +755,15 @@ static PVRSRV_ERROR SetDCSrcRect(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(psRect);
 
-       
+       /* Only full display swapchains on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCDstColourKey
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCDstColourKey(IMG_HANDLE hDevice,
                                       IMG_HANDLE hSwapChain,
                                       IMG_UINT32 ui32CKColour)
@@ -605,11 +772,15 @@ static PVRSRV_ERROR SetDCDstColourKey(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(ui32CKColour);
 
-       
+       /* Don't support DST CK on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCSrcColourKey
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCSrcColourKey(IMG_HANDLE hDevice,
                                       IMG_HANDLE hSwapChain,
                                       IMG_UINT32 ui32CKColour)
@@ -618,11 +789,15 @@ static PVRSRV_ERROR SetDCSrcColourKey(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(ui32CKColour);
 
-       
+       /* Don't support SRC CK on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * GetDCBuffers
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
                                  IMG_HANDLE hSwapChain,
                                  IMG_UINT32 *pui32BufferCount,
@@ -633,7 +808,7 @@ static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
        PVRSRV_ERROR eError;
        unsigned i;
        
-       
+       /* Check parameters */
        if(!hDevice 
        || !hSwapChain
        || !pui32BufferCount
@@ -656,10 +831,10 @@ static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
                goto Exit;
        }
        
-       
+       /* Return the buffer count */
        *pui32BufferCount = (IMG_UINT32)psSwapChain->ulBufferCount;
        
-       
+       /* Return the buffers */
        for(i=0; i<psSwapChain->ulBufferCount; i++)
        {
                phBuffer[i] = (IMG_HANDLE)&psSwapChain->psBuffer[i];
@@ -673,6 +848,10 @@ Exit:
        return eError;
 }
 
+/*
+ * SwapToDCBuffer
+ * Called from services.
+ */
 static PVRSRV_ERROR SwapToDCBuffer(IMG_HANDLE hDevice,
                                    IMG_HANDLE hBuffer,
                                    IMG_UINT32 ui32SwapInterval,
@@ -687,21 +866,17 @@ static PVRSRV_ERROR SwapToDCBuffer(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(ui32ClipRectCount);
        UNREFERENCED_PARAMETER(psClipRect);
        
-       
+       /* * Nothing to do since Services common code does the work */
 
        return PVRSRV_OK;
 }
 
-static PVRSRV_ERROR SwapToDCSystem(IMG_HANDLE hDevice,
-                                   IMG_HANDLE hSwapChain)
-{
-       UNREFERENCED_PARAMETER(hDevice);
-       UNREFERENCED_PARAMETER(hSwapChain);
-       
-       
-       return PVRSRV_OK;
-}
-
+/*
+ * Called after the screen has unblanked, or after any other occasion
+ * when we didn't wait for vsync, but now need to. Not doing this after
+ * unblank leads to screen jitter on some screens.
+ * Returns true if the screen has been deemed to have settled.
+ */
 static OMAPLFB_BOOL WaitForVSyncSettle(OMAPLFB_DEVINFO *psDevInfo)
 {
                unsigned i;
@@ -716,11 +891,20 @@ static OMAPLFB_BOOL WaitForVSyncSettle(OMAPLFB_DEVINFO *psDevInfo)
                return OMAPLFB_TRUE;
 }
 
+/*
+ * Swap handler.
+ * Called from the swap chain work queue handler.
+ * There is no need to take the swap chain creation lock in here, or use
+ * some other method of stopping the swap chain from being destroyed.
+ * This is because the swap chain creation lock is taken when queueing work,
+ * and the work queue is flushed before the swap chain is destroyed.
+ */
 void OMAPLFBSwapHandler(OMAPLFB_BUFFER *psBuffer)
 {
        OMAPLFB_DEVINFO *psDevInfo = psBuffer->psDevInfo;
        OMAPLFB_SWAPCHAIN *psSwapChain = psDevInfo->psSwapChain;
        OMAPLFB_BOOL bPreviouslyNotVSynced;
+
 #if defined(SUPPORT_DRI_DRM)
        if (!OMAPLFBAtomicBoolRead(&psDevInfo->sLeaveVT))
 #endif
@@ -763,63 +947,249 @@ void OMAPLFBSwapHandler(OMAPLFB_BUFFER *psBuffer)
                                break;
                }
        }
+
        psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete((IMG_HANDLE)psBuffer->hCmdComplete, IMG_TRUE);
 }
 
+/* Triggered by PVRSRVSwapToDCBuffer */
+static IMG_BOOL ProcessFlipV1(IMG_HANDLE hCmdCookie,
+                                                         OMAPLFB_DEVINFO *psDevInfo,
+                                                         OMAPLFB_SWAPCHAIN *psSwapChain,
+                                                         OMAPLFB_BUFFER *psBuffer,
+                                                         unsigned long ulSwapInterval)
+{
+       OMAPLFBCreateSwapChainLock(psDevInfo);
+
+       /* The swap chain has been destroyed */
+       if (SwapChainHasChanged(psDevInfo, psSwapChain))
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX
+                       ": %s: Device %u (PVR Device ID %u): The swap chain has been destroyed\n",
+                       __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
+       }
+       else
+       {
+               psBuffer->hCmdComplete = (OMAPLFB_HANDLE)hCmdCookie;
+               psBuffer->ulSwapInterval = ulSwapInterval;
+#if defined(CONFIG_DSSCOMP)
+               if (is_tiler_addr(psBuffer->sSysAddr.uiAddr))
+               {
+                       IMG_UINT32 w = psBuffer->psDevInfo->sDisplayDim.ui32Width;
+                       IMG_UINT32 h = psBuffer->psDevInfo->sDisplayDim.ui32Height;
+                       struct dsscomp_setup_dispc_data comp = {
+                               .num_mgrs = 1,
+                               .mgrs[0].alpha_blending = 1,
+                               .num_ovls = 1,
+                               .ovls[0].cfg =
+                               {
+                                       .width = w,
+                                       .win.w = w,
+                                       .crop.w = w,
+                                       .height = h,
+                                       .win.h = h,
+                                       .crop.h = h,
+                                       .stride = psBuffer->psDevInfo->sDisplayDim.ui32ByteStride,
+                                       .color_mode = OMAP_DSS_COLOR_ARGB32,
+                                       .enabled = 1,
+                                       .global_alpha = 255,
+                               },
+                               .mode = DSSCOMP_SETUP_DISPLAY,
+                       };
+                       struct tiler_pa_info *pas[1] = { NULL };
+                       comp.ovls[0].ba = (u32) psBuffer->sSysAddr.uiAddr;
+                       dsscomp_gralloc_queue(&comp, pas, true,
+                                                                 (void *) psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete,
+                                                                 (void *) psBuffer->hCmdComplete);
+               }
+               else
+#endif /* defined(CONFIG_DSSCOMP) */
+               {
+                       OMAPLFBQueueBufferForSwap(psSwapChain, psBuffer);
+               }
+       }
+
+       OMAPLFBCreateSwapChainUnLock(psDevInfo);
+
+       return IMG_TRUE;
+}
+
+#if defined(CONFIG_DSSCOMP)
+
+/* Triggered by PVRSRVSwapToDCBuffer2 */
+static IMG_BOOL ProcessFlipV2(IMG_HANDLE hCmdCookie,
+                                                         OMAPLFB_DEVINFO *psDevInfo,
+                                                         PDC_MEM_INFO *ppsMemInfos,
+                                                         IMG_UINT32 ui32NumMemInfos,
+                                                         struct dsscomp_setup_dispc_data *psDssData,
+                                                         IMG_UINT32 ui32DssDataLength)
+{
+       struct tiler_pa_info *apsTilerPAs[5];
+       IMG_UINT32 i, k;
+
+       if(ui32DssDataLength != sizeof(*psDssData))
+       {
+               WARN(1, "invalid size of private data (%d vs %d)",
+                        ui32DssDataLength, sizeof(*psDssData));
+               return IMG_FALSE;
+       }
+
+       if(psDssData->num_ovls == 0 || ui32NumMemInfos == 0)
+       {
+               WARN(1, "must have at least one layer");
+               return IMG_FALSE;
+       }
+
+       for(i = k = 0; i < ui32NumMemInfos && k < ARRAY_SIZE(apsTilerPAs); i++, k++)
+       {
+               struct tiler_pa_info *psTilerInfo;
+               IMG_CPU_VIRTADDR virtAddr;
+               IMG_CPU_PHYADDR phyAddr;
+               IMG_UINT32 ui32NumPages;
+               IMG_SIZE_T uByteSize;
+               int j;
+
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetByteSize(ppsMemInfos[i], &uByteSize);
+               ui32NumPages = (uByteSize + PAGE_SIZE - 1) >> PAGE_SHIFT;
+
+               apsTilerPAs[k] = NULL;
+
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], 0, &phyAddr);
+
+               /* NV12 buffers are already mapped to tiler */
+               if(psDssData->ovls[k].cfg.color_mode == OMAP_DSS_COLOR_NV12)
+               {
+                       psDssData->ovls[k].ba = (u32)phyAddr.uiAddr;
+
+                       psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], (uByteSize * 2) / 3, &phyAddr);
+                       psDssData->ovls[k].uv = (u32)phyAddr.uiAddr;
+                       continue;
+               }
+
+               /* Other kinds of buffer may also already be mapped to tiler */
+               if(is_tiler_addr((u32)phyAddr.uiAddr))
+               {
+                       psDssData->ovls[k].ba = (u32)phyAddr.uiAddr;
+                       continue;
+               }
+
+               psTilerInfo = kzalloc(sizeof(*psTilerInfo), GFP_KERNEL);
+               if(!psTilerInfo)
+               {
+                       continue;
+               }
+
+               psTilerInfo->mem = kzalloc(sizeof(*psTilerInfo->mem) * ui32NumPages, GFP_KERNEL);
+               if(!psTilerInfo->mem)
+               {
+                       kfree(psTilerInfo);
+                       continue;
+               }
+
+               psTilerInfo->num_pg = ui32NumPages;
+               psTilerInfo->memtype = TILER_MEM_USING;
+
+               for(j = 0; j < ui32NumPages; j++)
+               {
+                       psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], j << PAGE_SHIFT, &phyAddr);
+                       psTilerInfo->mem[j] = (u32)phyAddr.uiAddr;
+               }
+
+               /* Need base address for in-page offset */
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuVAddr(ppsMemInfos[i], &virtAddr);
+               psDssData->ovls[k].ba = (u32)virtAddr;
+               apsTilerPAs[k] = psTilerInfo;
+       }
+
+       /* Set up cloned layer addresses (but don't duplicate tiler_pas) */
+       for(i = k; i < psDssData->num_ovls && i < ARRAY_SIZE(apsTilerPAs); i++)
+       {
+               unsigned int ix = psDssData->ovls[i].ba;
+               if(ix >= ARRAY_SIZE(apsTilerPAs))
+               {
+                       WARN(1, "Invalid clone layer (%u); skipping all cloned layers", ix);
+                       psDssData->num_ovls = k;
+                       break;
+               }
+               apsTilerPAs[i] = apsTilerPAs[ix];
+               psDssData->ovls[i].ba = psDssData->ovls[ix].ba;
+               psDssData->ovls[i].uv = psDssData->ovls[ix].uv;
+       }
+
+       dsscomp_gralloc_queue(psDssData, apsTilerPAs, false,
+                                                 (void *)psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete,
+                                                 (void *)hCmdCookie);
+
+       for(i = 0; i < k; i++)
+       {
+               tiler_pa_free(apsTilerPAs[i]);
+       }
+
+       return IMG_TRUE;
+}
+
+#endif /* defined(CONFIG_DSSCOMP) */
+
+/* Command processing flip handler function.  Called from services. */
 static IMG_BOOL ProcessFlip(IMG_HANDLE  hCmdCookie,
                             IMG_UINT32  ui32DataSize,
                             IMG_VOID   *pvData)
 {
        DISPLAYCLASS_FLIP_COMMAND *psFlipCmd;
        OMAPLFB_DEVINFO *psDevInfo;
-       OMAPLFB_BUFFER *psBuffer;
-       OMAPLFB_SWAPCHAIN *psSwapChain;
 
-       
+       /* Check parameters  */
        if(!hCmdCookie || !pvData)
        {
                return IMG_FALSE;
        }
 
-       
+       /* Validate data packet  */
        psFlipCmd = (DISPLAYCLASS_FLIP_COMMAND*)pvData;
 
-       if (psFlipCmd == IMG_NULL || sizeof(DISPLAYCLASS_FLIP_COMMAND) != ui32DataSize)
+       if (psFlipCmd == IMG_NULL)
        {
                return IMG_FALSE;
        }
 
-       
        psDevInfo = (OMAPLFB_DEVINFO*)psFlipCmd->hExtDevice;
-       psBuffer = (OMAPLFB_BUFFER*)psFlipCmd->hExtBuffer;
-       psSwapChain = (OMAPLFB_SWAPCHAIN*) psFlipCmd->hExtSwapChain;
 
-       OMAPLFBCreateSwapChainLock(psDevInfo);
-
-       if (SwapChainHasChanged(psDevInfo, psSwapChain))
+       if(psFlipCmd->hExtBuffer)
        {
-               
-               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX
-                       ": %s: Device %u (PVR Device ID %u): The swap chain has been destroyed\n",
-                       __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
+               return ProcessFlipV1(hCmdCookie,
+                                                        psDevInfo,
+                                                        psFlipCmd->hExtSwapChain,
+                                                        psFlipCmd->hExtBuffer,
+                                                        psFlipCmd->ui32SwapInterval);
        }
        else
        {
-               psBuffer->hCmdComplete = (OMAPLFB_HANDLE)hCmdCookie;
-               psBuffer->ulSwapInterval = (unsigned long)psFlipCmd->ui32SwapInterval;
-#if defined(NO_HARDWARE)
-               psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete((IMG_HANDLE)psBuffer->hCmdComplete, IMG_FALSE);
+#if defined(CONFIG_DSSCOMP)
+               DISPLAYCLASS_FLIP_COMMAND2 *psFlipCmd2;
+               psFlipCmd2 = (DISPLAYCLASS_FLIP_COMMAND2 *)pvData;
+               return ProcessFlipV2(hCmdCookie,
+                                                        psDevInfo,
+                                                        psFlipCmd2->ppsMemInfos,
+                                                        psFlipCmd2->ui32NumMemInfos,
+                                                        psFlipCmd2->pvPrivData,
+                                                        psFlipCmd2->ui32PrivDataLength);
 #else
-               OMAPLFBQueueBufferForSwap(psSwapChain, psBuffer);
+               BUG();
 #endif
        }
+}
 
-       OMAPLFBCreateSwapChainUnLock(psDevInfo);
+/*!
+******************************************************************************
 
-       return IMG_TRUE;
-}
+ @Function     OMAPLFBInitFBDev
+ @Description specifies devices in the systems memory map
+ @Input    psSysData - sys data
 
+ @Return   OMAPLFB_ERROR  :
 
+******************************************************************************/
 static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
 {
        struct fb_info *psLINFBInfo;
@@ -829,11 +1199,8 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        unsigned long FBSize;
        unsigned long ulLCM;
        unsigned uiFBDevID = psDevInfo->uiFBDevID;
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-       acquire_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_LOCK();
 
        psLINFBInfo = registered_fb[uiFBDevID];
        if (psLINFBInfo == NULL)
@@ -846,7 +1213,10 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
                                        psLINFBInfo->screen_size :
                                        psLINFBInfo->fix.smem_len;
 
-       
+       /*
+        * Try and filter out invalid FB info structures (a problem
+        * seen on some OMAP3 systems).
+        */
        if (FBSize == 0 || psLINFBInfo->fix.line_length == 0)
        {
                eError = OMAPLFB_ERROR_INVALID_DEVICE;
@@ -908,7 +1278,87 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
                        ": Device %u: LCM of stride and page size: %lu\n",
                        psDevInfo->uiFBDevID, ulLCM));
 
-       
+       /* Additional implementation specific information */
+       OMAPLFBPrintInfo(psDevInfo);
+
+#if defined(CONFIG_DSSCOMP)
+       {
+               /* for some reason we need at least 3 buffers in the swap chain */
+               int n = FBSize / RoundUpToMultiple(psLINFBInfo->fix.line_length * psLINFBInfo->var.yres, ulLCM);
+               int res;
+               int i, x, y, w;
+               ion_phys_addr_t phys;
+               size_t size;
+               struct tiler_view_t view;
+
+               struct omap_ion_tiler_alloc_data sAllocData =
+               {
+                       /* TILER will align width to 128-bytes */
+                       /* however, SGX must have full page width */
+                       .w = ALIGN(psLINFBInfo->var.xres, PAGE_SIZE / (psLINFBInfo->var.bits_per_pixel / 8)),
+                       .h = psLINFBInfo->var.yres,
+                       .fmt = psLINFBInfo->var.bits_per_pixel == 16 ? TILER_PIXEL_FMT_16BIT : TILER_PIXEL_FMT_32BIT,
+                       .flags = 0,
+               };
+
+               printk(KERN_DEBUG DRIVER_PREFIX
+                          " %s: Device %u: Requesting %d TILER 2D framebuffers\n",
+                          __FUNCTION__, uiFBDevID, n);
+
+               /* INTEGRATION_POINT: limit to MAX 3 FBs to save TILER container space */
+               if (n > 3)
+                       n = 3;
+
+               sAllocData.w *= n;
+
+               psPVRFBInfo->uiBytesPerPixel = psLINFBInfo->var.bits_per_pixel >> 3;
+               psPVRFBInfo->bIs2D = OMAPLFB_TRUE;
+
+               res = omap_ion_tiler_alloc(gpsIONClient, &sAllocData);
+               psPVRFBInfo->psIONHandle = sAllocData.handle;
+               if (res < 0)
+               {
+                       printk(KERN_ERR DRIVER_PREFIX
+                                  " %s: Device %u: Could not allocate 2D framebuffer(%d)\n",
+                                  __FUNCTION__, uiFBDevID, res);
+                       goto ErrorModPut;
+               }
+
+               psLINFBInfo->fix.smem_start = ion_phys(gpsIONClient, sAllocData.handle, &phys, &size);
+
+               psPVRFBInfo->sSysAddr.uiAddr = phys;
+               psPVRFBInfo->sCPUVAddr = 0;
+               psPVRFBInfo->ulWidth = psLINFBInfo->var.xres;
+               psPVRFBInfo->ulHeight = psLINFBInfo->var.yres;
+
+               psPVRFBInfo->ulByteStride = PAGE_ALIGN(psPVRFBInfo->ulWidth * psPVRFBInfo->uiBytesPerPixel);
+               w = psPVRFBInfo->ulByteStride >> PAGE_SHIFT;
+               /* this is an "effective" FB size to get correct number of buffers */
+               psPVRFBInfo->ulFBSize = sAllocData.h * n * psPVRFBInfo->ulByteStride;
+               psPVRFBInfo->psPageList = kzalloc(w * n * psPVRFBInfo->ulHeight * sizeof(*psPVRFBInfo->psPageList), GFP_KERNEL);
+               if (!psPVRFBInfo->psPageList)
+               {
+                       printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Could not allocate page list\n", __FUNCTION__, psDevInfo->uiFBDevID);
+                       ion_free(gpsIONClient, sAllocData.handle);
+                       goto ErrorModPut;
+               }
+
+               tilview_create(&view, phys, psDevInfo->sFBInfo.ulWidth, psDevInfo->sFBInfo.ulHeight);
+               for(i = 0; i < n; i++)
+               {
+                       for(y = 0; y < psDevInfo->sFBInfo.ulHeight; y++)
+                       {
+                               for(x = 0; x < w; x++)
+                               {
+                                       psPVRFBInfo->psPageList[i * psDevInfo->sFBInfo.ulHeight * w + y * w + x].uiAddr =
+                                       phys + view.v_inc * y + ((x + i * w) << PAGE_SHIFT);
+                               }
+                       }
+               }
+       }
+#else /* defined(CONFIG_DSSCOMP) */
+       /* System Surface */
        psPVRFBInfo->sSysAddr.uiAddr = psLINFBInfo->fix.smem_start;
        psPVRFBInfo->sCPUVAddr = psLINFBInfo->screen_base;
 
@@ -916,8 +1366,15 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        psPVRFBInfo->ulHeight = psLINFBInfo->var.yres;
        psPVRFBInfo->ulByteStride =  psLINFBInfo->fix.line_length;
        psPVRFBInfo->ulFBSize = FBSize;
+#endif /* defined(CONFIG_DSSCOMP) */
+
        psPVRFBInfo->ulBufferSize = psPVRFBInfo->ulHeight * psPVRFBInfo->ulByteStride;
-       
+
+       /* Round the buffer size up to a multiple of the number of pages
+        * and the byte stride.
+        * This is used internally, to ensure buffers start on page
+        * boundaries, for the benefit of PVR Services.
+        */
        psPVRFBInfo->ulRoundedBufferSize = RoundUpToMultiple(psPVRFBInfo->ulBufferSize, ulLCM);
 
        if(psLINFBInfo->var.bits_per_pixel == 16)
@@ -965,7 +1422,7 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        psDevInfo->sFBInfo.ulPhysicalHeightmm =
                ((int)psLINFBInfo->var.height > 0) ? psLINFBInfo->var.height : 54;
 
-       
+       /* System Surface */
        psDevInfo->sFBInfo.sSysAddr.uiAddr = psPVRFBInfo->sSysAddr.uiAddr;
        psDevInfo->sFBInfo.sCPUVAddr = psPVRFBInfo->sCPUVAddr;
 
@@ -975,11 +1432,7 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
 ErrorModPut:
        module_put(psLINFBOwner);
 ErrorRelSem:
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-       release_console_sem();
-#endif
+       OMAPLFB_CONSOLE_UNLOCK();
 
        return eError;
 }
@@ -988,11 +1441,19 @@ static void OMAPLFBDeInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
 {
        struct fb_info *psLINFBInfo = psDevInfo->psLINFBInfo;
        struct module *psLINFBOwner;
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-       acquire_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_LOCK();
+
+#if defined(CONFIG_DSSCOMP)
+       {
+               OMAPLFB_FBINFO *psPVRFBInfo = &psDevInfo->sFBInfo;
+               kfree(psPVRFBInfo->psPageList);
+               if (psPVRFBInfo->psIONHandle)
+               {
+                       ion_free(gpsIONClient, psPVRFBInfo->psIONHandle);
+               }
+       }
+#endif /* defined(CONFIG_DSSCOMP) */
 
        psLINFBOwner = psLINFBInfo->fbops->owner;
 
@@ -1002,11 +1463,8 @@ static void OMAPLFBDeInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        }
 
        module_put(psLINFBOwner);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-       release_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_UNLOCK();
 }
 
 static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
@@ -1015,7 +1473,7 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
        IMG_UINT32              aui32SyncCountList[OMAPLFB_COMMAND_COUNT][2];
        OMAPLFB_DEVINFO         *psDevInfo = NULL;
 
-       
+       /* Allocate device info. structure */
        psDevInfo = (OMAPLFB_DEVINFO *)OMAPLFBAllocKernelMem(sizeof(OMAPLFB_DEVINFO));
 
        if(psDevInfo == NULL)
@@ -1026,21 +1484,26 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                goto ErrorExit;
        }
 
-       
+       /* Any fields not set will be zero */
        memset(psDevInfo, 0, sizeof(OMAPLFB_DEVINFO));
 
        psDevInfo->uiFBDevID = uiFBDevID;
 
-       
+       /* Get the kernel services function table */
        if(!(*gpfnGetPVRJTable)(&psDevInfo->sPVRJTable))
        {
                goto ErrorFreeDevInfo;
        }
 
-#ifdef FBDEV_PRESENT   
+       /* Save private fbdev information structure in the dev. info. */
        if(OMAPLFBInitFBDev(psDevInfo) != OMAPLFB_OK)
        {
-               
+               /*
+                * Leave it to OMAPLFBInitFBDev to print an error message, if
+                * required.  The function may have failed because
+                * there is no Linux framebuffer device corresponding
+                * to the device ID.
+                */
                goto ErrorFreeDevInfo;
        }
 
@@ -1065,24 +1528,16 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                ": Device %u: Maximum number of swap chain buffers: %u\n",
                psDevInfo->uiFBDevID, psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers));
 
-       
+       /* Setup system buffer */
        psDevInfo->sSystemBuffer.sSysAddr = psDevInfo->sFBInfo.sSysAddr;
        psDevInfo->sSystemBuffer.sCPUVAddr = psDevInfo->sFBInfo.sCPUVAddr;
        psDevInfo->sSystemBuffer.psDevInfo = psDevInfo;
 
        OMAPLFBInitBufferForSwap(&psDevInfo->sSystemBuffer);
-#else
-                psDevInfo->sSystemBuffer.sCPUVAddr = 0x100;
-//                psDevInfo->sSystemBuffer.ulBufferSize = 600*3200;
-
-                psDevInfo->sDisplayFormat.pixelformat = 20;
-                psDevInfo->sFBInfo.ulWidth      =  800;
-                psDevInfo->sFBInfo.ulHeight     =  600;
-                psDevInfo->sFBInfo.ulByteStride =  3200;
-                psDevInfo->sFBInfo.ulFBSize     =  8388608;
-                psDevInfo->sFBInfo.ulBufferSize = 600*3200;
-#endif
 
+       /*
+               Setup the DC Jtable so SRVKM can call into this driver
+       */
        psDevInfo->sDCJTable.ui32TableSize = sizeof(PVRSRV_DC_SRV2DISP_KMJTABLE);
        psDevInfo->sDCJTable.pfnOpenDCDevice = OpenDCDevice;
        psDevInfo->sDCJTable.pfnCloseDCDevice = CloseDCDevice;
@@ -1099,10 +1554,9 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
        psDevInfo->sDCJTable.pfnSetDCSrcColourKey = SetDCSrcColourKey;
        psDevInfo->sDCJTable.pfnGetDCBuffers = GetDCBuffers;
        psDevInfo->sDCJTable.pfnSwapToDCBuffer = SwapToDCBuffer;
-       psDevInfo->sDCJTable.pfnSwapToDCSystem = SwapToDCSystem;
        psDevInfo->sDCJTable.pfnSetDCState = SetDCState;
 
-       
+       /* Register device with services and retrieve device index */
        if(psDevInfo->sPVRJTable.pfnPVRSRVRegisterDCDevice(
                &psDevInfo->sDCJTable,
                &psDevInfo->uiPVRDevID) != PVRSRV_OK)
@@ -1116,17 +1570,18 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                ": Device %u: PVR Device ID: %u\n",
                psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
        
-       
+       /* Setup private command processing function table ... */
        pfnCmdProcList[DC_FLIP_COMMAND] = ProcessFlip;
 
-       
-       aui32SyncCountList[DC_FLIP_COMMAND][0] = 0; 
-       aui32SyncCountList[DC_FLIP_COMMAND][1] = 2; 
-
-       
-
-
+       /* ... and associated sync count(s) */
+       aui32SyncCountList[DC_FLIP_COMMAND][0] = 0; /* writes */
+       aui32SyncCountList[DC_FLIP_COMMAND][1] = 10; /* reads */
 
+       /*
+               Register private command processing functions with
+               the Command Queue Manager and setup the general
+               command complete function in the devinfo.
+       */
        if (psDevInfo->sPVRJTable.pfnPVRSRVRegisterCmdProcList(psDevInfo->uiPVRDevID,
                                                                                                                        &pfnCmdProcList[0],
                                                                                                                        aui32SyncCountList,
@@ -1171,14 +1626,18 @@ OMAPLFB_ERROR OMAPLFBInit(void)
                return OMAPLFB_ERROR_INIT_FAILURE;
        }
 
-       
+       /*
+        * We search for frame buffer devices backwards, as the last device
+        * registered with PVR Services will be the first device enumerated
+        * by PVR Services.
+        */
        for(i = uiMaxFBDevIDPlusOne; i-- != 0;)
        {
                OMAPLFB_DEVINFO *psDevInfo = OMAPLFBInitDev(i);
 
                if (psDevInfo != NULL)
                {
-                       
+                       /* Set the top-level anchor */
                        OMAPLFBSetDevInfoPtr(psDevInfo->uiFBDevID, psDevInfo);
                        uiDevicesFound++;
                }
@@ -1187,6 +1646,10 @@ OMAPLFB_ERROR OMAPLFBInit(void)
        return (uiDevicesFound != 0) ? OMAPLFB_OK : OMAPLFB_ERROR_INIT_FAILURE;
 }
 
+/*
+ *     OMAPLFBDeInitDev
+ *     DeInitialises one device
+ */
 static OMAPLFB_BOOL OMAPLFBDeInitDev(OMAPLFB_DEVINFO *psDevInfo)
 {
        PVRSRV_DC_DISP2SRV_KMJTABLE *psPVRJTable = &psDevInfo->sPVRJTable;
@@ -1211,25 +1674,31 @@ static OMAPLFB_BOOL OMAPLFBDeInitDev(OMAPLFB_DEVINFO *psDevInfo)
                return OMAPLFB_FALSE;
        }
 
-       
+       /*
+        * Remove display class device from kernel services device
+        * register.
+        */
        if (psPVRJTable->pfnPVRSRVRemoveDCDevice(psDevInfo->uiPVRDevID) != PVRSRV_OK)
        {
                printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: PVR Device %u: Couldn't remove device from PVR Services\n", __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID);
                return OMAPLFB_FALSE;
        }
-#ifdef FBDEV_PRESENT   
+       
        OMAPLFBDeInitFBDev(psDevInfo);
-#endif
 
        OMAPLFBSetDevInfoPtr(psDevInfo->uiFBDevID, NULL);
 
-       
+       /* De-allocate data structure */
        OMAPLFBFreeKernelMem(psDevInfo);
 
        return OMAPLFB_TRUE;
 }
 
+/*
+ *     OMAPLFBDeInit
+ *     Deinitialises the display class device component of the FBDev
+ */
 OMAPLFB_ERROR OMAPLFBDeInit(void)
 {
        unsigned uiMaxFBDevIDPlusOne = OMAPLFBMaxFBDevIDPlusOne();
@@ -1249,3 +1718,7 @@ OMAPLFB_ERROR OMAPLFBDeInit(void)
        return (bError) ? OMAPLFB_ERROR_INIT_FAILURE : OMAPLFB_OK;
 }
 
+/******************************************************************************
+ End of file (omaplfb_displayclass.c)
+******************************************************************************/
+
index 85f5e5e..1184fb6 100644 (file)
@@ -1,38 +1,80 @@
-/**********************************************************************
- *
- * Copyright(c) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          OMAP linux display driver components
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with 3rd Party display hardware.  It is NOT a specification for
+ a display controller driver, rather a specification to extend the API for a
+ pre-existing driver for the display hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying display hardware, allowing
+ the client drivers to indirectly control the display hardware and access its
+ associated memory.
+ Functions of the API include
+ - query primary surface attributes (width, height, stride, pixel format, CPU
+     physical and virtual address)
+ - swap/flip chain creation and subsequent query of surface attributes
+ - asynchronous display surface flipping, taking account of asynchronous read
+ (flip) and write (render) operations to the display surface
+
+ Note: having queried surface attributes the client drivers are able to map the
+ display memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the display surface handle.
+
+ This code is intended to be an example of how a pre-existing display driver may
+ be extended to support the 3rd Party Display interface to POWERVR Services
+ - IMG is not providing a display driver implementation.
+ **************************************************************************/
 
 #include <linux/version.h>
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,38)
+
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,38))
 #ifndef AUTOCONF_INCLUDED
 #include <linux/config.h>
 #endif
 #endif
 
-
 #include <asm/atomic.h>
 
 #if defined(SUPPORT_DRI_DRM)
 #include <linux/omapfb.h>
 #include <linux/mutex.h>
 
-//# include <plat/vrfb.h>
+#if defined(PVR_OMAPLFB_DRM_FB)
+#include <plat/display.h>
+#include <linux/omap_gpu.h>
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+/* OmapZoom.org OMAP3 2.6.29 kernel tree       - Needs mach/vrfb.h
+ * OmapZoom.org OMAP3 2.6.32 kernel tree       - No additional header required
+ * OmapZoom.org OMAP4 2.6.33 kernel tree       - No additional header required
+ * OmapZoom.org OMAP4 2.6.34 kernel tree       - Needs plat/vrfb.h
+ * Sholes 2.6.32 kernel tree                   - Needs plat/vrfb.h
+ */
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,34))
 #define PVR_OMAPFB3_NEEDS_PLAT_VRFB_H
 #endif
 
 #if defined(PVR_OMAPFB3_NEEDS_PLAT_VRFB_H)
-# include <plat/vrfb.h>
+#include <plat/vrfb.h>
 #else
-# if defined(PVR_OMAPFB3_NEEDS_MACH_VRFB_H)
-#  include <mach/vrfb.h>
-# endif
+#if defined(PVR_OMAPFB3_NEEDS_MACH_VRFB_H)
+#include <mach/vrfb.h>
+#endif
 #endif
 
 #if defined(DEBUG)
 #define        DEBUG PVR_DEBUG
 #undef PVR_DEBUG
 #endif
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
+
+#if defined(CONFIG_DSSCOMP)
+#include <mach/tiler.h>
+#include <video/dsscomp.h>
+#include <plat/dsscomp.h>
+#endif /* defined(CONFIG_DSSCOMP) */
 
 #include "img_defs.h"
 #include "servicesext.h"
 
 MODULE_SUPPORTED_DEVICE(DEVNAME);
 
+#if !defined(PVR_OMAPLFB_DRM_FB)
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,34))
 #define OMAP_DSS_DRIVER(drv, dev) struct omap_dss_driver *drv = (dev) != NULL ? (dev)->driver : NULL
 #define OMAP_DSS_MANAGER(man, dev) struct omap_overlay_manager *man = (dev) != NULL ? (dev)->manager : NULL
@@ -102,7 +161,7 @@ MODULE_SUPPORTED_DEVICE(DEVNAME);
 #define OMAP_DSS_MANAGER(man, dev) struct omap_dss_device *man = (dev)
 #define        WAIT_FOR_VSYNC(man)     ((man)->wait_vsync)
 #endif
-
+#endif /* !defined(PVR_OMAPLFB_DRM_FB) */
 
 void *OMAPLFBAllocKernelMem(unsigned long ulSize)
 {
@@ -184,12 +243,13 @@ OMAPLFB_ERROR OMAPLFBGetLibFuncAddr (char *szFunctionName, PFN_DC_GET_PVRJTABLE
                return (OMAPLFB_ERROR_INVALID_PARAMS);
        }
 
-       
+       /* Nothing to do - should be exported from pvrsrv.ko */
        *ppfnFuncTable = PVRGetDisplayClassJTable;
 
        return (OMAPLFB_OK);
 }
 
+/* Inset a swap buffer into the swap chain work queue */
 void OMAPLFBQueueBufferForSwap(OMAPLFB_SWAPCHAIN *psSwapChain, OMAPLFB_BUFFER *psBuffer)
 {
        int res = queue_work(psSwapChain->psWorkQueue, &psBuffer->sWork);
@@ -200,6 +260,7 @@ void OMAPLFBQueueBufferForSwap(OMAPLFB_SWAPCHAIN *psSwapChain, OMAPLFB_BUFFER *p
        }
 }
 
+/* Process an item on a swap chain work queue */
 static void WorkQueueHandler(struct work_struct *psWork)
 {
        OMAPLFB_BUFFER *psBuffer = container_of(psWork, OMAPLFB_BUFFER, sWork);
@@ -207,16 +268,37 @@ static void WorkQueueHandler(struct work_struct *psWork)
        OMAPLFBSwapHandler(psBuffer);
 }
 
+/* Create a swap chain work queue */
 OMAPLFB_ERROR OMAPLFBCreateSwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
 {
-#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,34))
-        psSwapChain->psWorkQueue = __create_workqueue(DEVNAME, 1, 1, 1);
-#else  
-       psSwapChain->psWorkQueue = create_workqueue(DEVNAME);
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37))
+       /*
+        * Calling alloc_ordered_workqueue with the WQ_FREEZABLE and
+        * WQ_MEM_RECLAIM flags set, (currently) has the same effect as
+        * calling create_freezable_workqueue. None of the other WQ
+        * flags are valid. Setting WQ_MEM_RECLAIM should allow the
+        * workqueue to continue to service the swap chain in low memory
+        * conditions, preventing the driver from holding on to
+        * resources longer than it needs to.
+        */
+       psSwapChain->psWorkQueue = alloc_ordered_workqueue(DEVNAME, WQ_FREEZEABLE | WQ_MEM_RECLAIM);
+#else
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36))
+       psSwapChain->psWorkQueue = create_freezable_workqueue(DEVNAME);
+#else
+       /*
+        * Create a single-threaded, freezable, rt-prio workqueue.
+        * Such workqueues are frozen with user threads when a system
+        * suspends, before driver suspend entry points are called.
+        * This ensures this driver will not call into the Linux
+        * framebuffer driver after the latter is suspended.
+        */
+       psSwapChain->psWorkQueue = __create_workqueue(DEVNAME, 1, 1, 1);
+#endif
 #endif
        if (psSwapChain->psWorkQueue == NULL)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: create_singlethreaded_workqueue failed\n", __FUNCTION__, psSwapChain->uiFBDevID);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: Couldn't create workqueue\n", __FUNCTION__, psSwapChain->uiFBDevID);
 
                return (OMAPLFB_ERROR_INIT_FAILURE);
        }
@@ -224,26 +306,26 @@ OMAPLFB_ERROR OMAPLFBCreateSwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
        return (OMAPLFB_OK);
 }
 
+/* Prepare buffer for insertion into a swap chain work queue */
 void OMAPLFBInitBufferForSwap(OMAPLFB_BUFFER *psBuffer)
 {
        INIT_WORK(&psBuffer->sWork, WorkQueueHandler);
 }
 
+/* Destroy a swap chain work queue */
 void OMAPLFBDestroySwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
 {
        destroy_workqueue(psSwapChain->psWorkQueue);
 }
 
+/* Flip display to given buffer */
 void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
 {
        struct fb_var_screeninfo sFBVar;
        int res;
        unsigned long ulYResVirtual;
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-       acquire_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_LOCK();
 
        sFBVar = psDevInfo->psLINFBInfo->var;
 
@@ -252,8 +334,62 @@ void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
 
        ulYResVirtual = psBuffer->ulYOffset + sFBVar.yres;
 
-       
+#if defined(CONFIG_DSSCOMP)
+       {
+               /*
+                * If using DSSCOMP, we need to use dsscomp queuing for normal
+                * framebuffer updates, so that previously used overlays get
+                * automatically disabled, and manager gets dirtied.  We can
+                * do that because DSSCOMP takes ownership of all pipelines on
+                * a manager.
+                */
+               struct fb_fix_screeninfo sFBFix = psDevInfo->psLINFBInfo->fix;
+               struct dsscomp_setup_dispc_data d =
+               {
+                       .num_ovls = 1,
+                       .num_mgrs = 1,
+                       .mgrs[0].alpha_blending = 1,
+                       .ovls[0] =
+                       {
+                               .cfg =
+                               {
+                                       .win.w = sFBVar.xres,
+                                       .win.h = sFBVar.yres,
+                                       .crop.x = sFBVar.xoffset,
+                                       .crop.y = sFBVar.yoffset,
+                                       .crop.w = sFBVar.xres,
+                                       .crop.h = sFBVar.yres,
+                                       .width = sFBVar.xres_virtual,
+                                       .height = sFBVar.yres_virtual,
+                                       .stride = sFBFix.line_length,
+                                       .enabled = 1,
+                                       .global_alpha = 255,
+                               },
+                       },
+               };
+
+               /* do not map buffer into TILER1D as it is contiguous */
+               struct tiler_pa_info *pas[] = { NULL };
+
+               d.ovls[0].ba = sFBFix.smem_start;
+               omapfb_mode_to_dss_mode(&sFBVar, &d.ovls[0].cfg.color_mode);
+
+               res = dsscomp_gralloc_queue(&d, pas, true, NULL, NULL);
+       }
+#else /* defined(CONFIG_DSSCOMP) */
+       /*
+        * PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY should be defined to work
+        * around flipping problems seen with the Taal LCDs on Blaze.
+        * The work around is safe to use with other types of screen on Blaze
+        * (e.g. HDMI) and on other platforms (e.g. Panda board).
+        */
+#if !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY)
+       /*
+        * Attempt to change the virtual screen resolution if it is too
+        * small.  Note that fb_set_var also pans the display.
+        */
        if (sFBVar.xres_virtual != sFBVar.xres || sFBVar.yres_virtual < ulYResVirtual)
+#endif /* !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY) */
        {
                sFBVar.xres_virtual = sFBVar.xres;
                sFBVar.yres_virtual = ulYResVirtual;
@@ -263,66 +399,293 @@ void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
                res = fb_set_var(psDevInfo->psLINFBInfo, &sFBVar);
                if (res != 0)
                {
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: fb_set_var failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: fb_set_var failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
                }
        }
+#if !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY)
        else
        {
                res = fb_pan_display(psDevInfo->psLINFBInfo, &sFBVar);
                if (res != 0)
                {
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: fb_pan_display failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: fb_pan_display failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
                }
        }
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-       release_console_sem();
+#endif /* !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY) */
+#endif /* defined(CONFIG_DSSCOMP) */
+
+       OMAPLFB_CONSOLE_UNLOCK();
+}
+
+#if !defined(PVR_OMAPLFB_DRM_FB) || defined(DEBUG)
+static OMAPLFB_BOOL OMAPLFBValidateDSSUpdateMode(enum omap_dss_update_mode eMode)
+{
+       switch (eMode)
+       {
+               case OMAP_DSS_UPDATE_AUTO:
+               case OMAP_DSS_UPDATE_MANUAL:
+               case OMAP_DSS_UPDATE_DISABLED:
+                       return OMAPLFB_TRUE;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_FALSE;
+}
+
+static OMAPLFB_UPDATE_MODE OMAPLFBFromDSSUpdateMode(enum omap_dss_update_mode eMode)
+{
+       switch (eMode)
+       {
+               case OMAP_DSS_UPDATE_AUTO:
+                       return OMAPLFB_UPDATE_MODE_AUTO;
+               case OMAP_DSS_UPDATE_MANUAL:
+                       return OMAPLFB_UPDATE_MODE_MANUAL;
+               case OMAP_DSS_UPDATE_DISABLED:
+                       return OMAPLFB_UPDATE_MODE_DISABLED;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_UPDATE_MODE_UNDEFINED;
+}
 #endif
+
+static OMAPLFB_BOOL OMAPLFBValidateUpdateMode(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return OMAPLFB_TRUE;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_FALSE;
+}
+
+static enum omap_dss_update_mode OMAPLFBToDSSUpdateMode(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+                       return OMAP_DSS_UPDATE_AUTO;
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+                       return OMAP_DSS_UPDATE_MANUAL;
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return OMAP_DSS_UPDATE_DISABLED;
+               default:
+                       break;
+       }
+
+       return -1;
+}
+
+#if defined(DEBUG)
+static const char *OMAPLFBUpdateModeToString(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+                       return "Auto Update Mode";
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+                       return "Manual Update Mode";
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return "Update Mode Disabled";
+               case OMAPLFB_UPDATE_MODE_UNDEFINED:
+                       return "Update Mode Undefined";
+               default:
+                       break;
+       }
+
+       return "Unknown Update Mode";
+}
+
+static const char *OMAPLFBDSSUpdateModeToString(enum omap_dss_update_mode eMode)
+{
+       if (!OMAPLFBValidateDSSUpdateMode(eMode))
+       {
+               return "Unknown Update Mode";
+       }
+
+       return OMAPLFBUpdateModeToString(OMAPLFBFromDSSUpdateMode(eMode));
+}
+
+void OMAPLFBPrintInfo(OMAPLFB_DEVINFO *psDevInfo)
+{
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       unsigned uConnectors;
+       unsigned uConnector;
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: DRM framebuffer\n", psDevInfo->uiFBDevID));
+
+       for (psConnector = NULL, uConnectors = 0;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               uConnectors++;
+       }
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: Number of screens (DRM connectors): %u\n", psDevInfo->uiFBDevID, uConnectors));
+
+       if (uConnectors == 0)
+       {
+               return;
+       }
+
+       for (psConnector = NULL, uConnector = 0;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL; uConnector++)
+       {
+               enum omap_dss_update_mode eMode = omap_connector_get_update_mode(psConnector);
+
+               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: Screen %u: %s (%d)\n", psDevInfo->uiFBDevID, uConnector, OMAPLFBDSSUpdateModeToString(eMode), (int)eMode));
+
+       }
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+       OMAPLFB_UPDATE_MODE eMode = OMAPLFBGetUpdateMode(psDevInfo);
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: non-DRM framebuffer\n", psDevInfo->uiFBDevID));
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: %s\n", psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 }
+#endif /* defined(DEBUG) */
 
+/* 
+ * Get display update mode.
+ * If the mode is AUTO, we can wait for VSync, if desired.
+ */
 OMAPLFB_UPDATE_MODE OMAPLFBGetUpdateMode(OMAPLFB_DEVINFO *psDevInfo)
 {
 #if LINUX_VERSION_CODE < KERNEL_VERSION(3,1,0)
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       OMAPLFB_UPDATE_MODE eMode = OMAPLFB_UPDATE_MODE_UNDEFINED;
+
+       /*
+        * There may be multiple displays connected. If at least one
+        * display is manual update mode, report all screens as being
+        * in that mode.
+        */
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               switch(omap_connector_get_update_mode(psConnector))
+               {
+                       case OMAP_DSS_UPDATE_MANUAL:
+                               eMode = OMAPLFB_UPDATE_MODE_MANUAL;
+                               break;
+                       case OMAP_DSS_UPDATE_DISABLED:
+                               if (eMode == OMAPLFB_UPDATE_MODE_UNDEFINED)
+                               {
+                                       eMode = OMAPLFB_UPDATE_MODE_DISABLED;
+                               }
+                               break;
+                       case OMAP_DSS_UPDATE_AUTO:
+                               /* Fall through to default case */
+                       default:
+                               /* Asssume auto update is possible */
+                               if (eMode != OMAPLFB_UPDATE_MODE_MANUAL)
+                               {
+                                       eMode = OMAPLFB_UPDATE_MODE_AUTO;
+                               }
+                               break;
+               }
+       }
+
+       return eMode;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
-       enum omap_dss_update_mode eMode;
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
-        if (psDSSDrv == NULL || psDSSDev == NULL)
-        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: No DSS device\n", __FUNCTION__, psDevInfo->uiFBDevID));
+
+       enum omap_dss_update_mode eMode;
+
+       if (psDSSDrv == NULL)
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No DSS device\n", __FUNCTION__, psDevInfo->uiFBDevID));
                return OMAPLFB_UPDATE_MODE_UNDEFINED;
-        }
+       }
 
        if (psDSSDrv->get_update_mode == NULL)
        {
-//             DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Can't get update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
-               return OMAPLFB_UPDATE_MODE_AUTO;
+               if (strcmp(psDSSDev->name, "hdmi") == 0)
+               {
+                       return OMAPLFB_UPDATE_MODE_AUTO;
+               }
+//             DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No get_update_mode function\n", __FUNCTION__, psDevInfo->uiFBDevID));
 //             return OMAPLFB_UPDATE_MODE_UNDEFINED;
+                       return OMAPLFB_UPDATE_MODE_AUTO;
        }
 
        eMode = psDSSDrv->get_update_mode(psDSSDev);
-       switch(eMode)
+       if (!OMAPLFBValidateDSSUpdateMode(eMode))
        {
-               case OMAP_DSS_UPDATE_AUTO:
-                       return OMAPLFB_UPDATE_MODE_AUTO;
-               case OMAP_DSS_UPDATE_MANUAL:
-                       return OMAPLFB_UPDATE_MODE_MANUAL;
-               case OMAP_DSS_UPDATE_DISABLED:
-                       return OMAPLFB_UPDATE_MODE_DISABLED;
-               default:
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eMode));
-                       break;
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
        }
 
-       return OMAPLFB_UPDATE_MODE_UNDEFINED;
+       return OMAPLFBFromDSSUpdateMode(eMode);
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 #else
-return OMAPLFB_UPDATE_MODE_AUTO;
+       return OMAPLFB_UPDATE_MODE_AUTO;
 #endif
 }
 
+/* Set display update mode */
 OMAPLFB_BOOL OMAPLFBSetUpdateMode(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_UPDATE_MODE eMode)
 {
 #if LINUX_VERSION_CODE < KERNEL_VERSION(3,1,0)
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       enum omap_dss_update_mode eDSSMode;
+       OMAPLFB_BOOL bSuccess = OMAPLFB_FALSE;
+       OMAPLFB_BOOL bFailure = OMAPLFB_FALSE;
+
+       if (!OMAPLFBValidateUpdateMode(eMode))
+       {
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
+                       return OMAPLFB_FALSE;
+       }
+       eDSSMode = OMAPLFBToDSSUpdateMode(eMode);
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               int iRes = omap_connector_set_update_mode(psConnector, eDSSMode);
+               OMAPLFB_BOOL bRes = (iRes == 0);
+
+
+               bSuccess |= bRes;
+               bFailure |= !bRes;
+       }
+
+       if (!bFailure)
+       {
+               if (!bSuccess)
+               {
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No screens\n", __FUNCTION__, psDevInfo->uiFBDevID));
+               }
+
+               return OMAPLFB_TRUE;
+       }
+
+       if (!bSuccess)
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set %s for any screen\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+               return OMAPLFB_FALSE;
+       }
+
+       if (eMode == OMAPLFB_UPDATE_MODE_AUTO)
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set %s for all screens\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+               return OMAPLFB_FALSE;
+       }
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: %s set for some screens\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
        enum omap_dss_update_mode eDSSMode;
@@ -330,41 +693,44 @@ OMAPLFB_BOOL OMAPLFBSetUpdateMode(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_UPDATE_MOD
 
        if (psDSSDrv == NULL || psDSSDrv->set_update_mode == NULL)
        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Can't set update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Can't set update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
                return OMAPLFB_FALSE;
        }
 
-       switch(eMode)
+       if (!OMAPLFBValidateUpdateMode(eMode))
        {
-               case OMAPLFB_UPDATE_MODE_AUTO:
-                       eDSSMode = OMAP_DSS_UPDATE_AUTO;
-                       break;
-               case OMAPLFB_UPDATE_MODE_MANUAL:
-                       eDSSMode = OMAP_DSS_UPDATE_MANUAL;
-                       break;
-               case OMAPLFB_UPDATE_MODE_DISABLED:
-                       eDSSMode = OMAP_DSS_UPDATE_DISABLED;
-                       break;
-               default:
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eMode));
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
                        return OMAPLFB_FALSE;
        }
+       eDSSMode = OMAPLFBToDSSUpdateMode(eMode);
 
        res = psDSSDrv->set_update_mode(psDSSDev, eDSSMode);
        if (res != 0)
        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: set_update_mode failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: set_update_mode (%s) failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBDSSUpdateModeToString(eDSSMode), res));
        }
 
        return (res == 0);
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 #else
 return 1;
 #endif
 }
 
+/* Wait for VSync */
 OMAPLFB_BOOL OMAPLFBWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
 {
-#ifdef FBDEV_PRESENT
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               (void) omap_encoder_wait_for_vsync(psConnector->encoder);
+       }
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_MANAGER(psDSSMan, psDSSDev);
 
@@ -373,16 +739,36 @@ OMAPLFB_BOOL OMAPLFBWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
                int res = WAIT_FOR_VSYNC(psDSSMan)(psDSSMan);
                if (res != 0)
                {
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Wait for vsync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Wait for vsync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
                        return OMAPLFB_FALSE;
                }
        }
-#endif
+
        return OMAPLFB_TRUE;
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 }
 
+/*
+ * Wait for screen to update.  If the screen is in manual or auto update
+ * mode, we can call this function to wait for the screen to update.
+ */
 OMAPLFB_BOOL OMAPLFBManualSync(OMAPLFB_DEVINFO *psDevInfo)
 {
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL; )
+       {
+               /* Try manual sync first, then try wait for vsync */
+               if (omap_connector_sync(psConnector) != 0)
+               {
+                       (void) omap_encoder_wait_for_vsync(psConnector->encoder);
+               }
+       }
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
 
@@ -391,13 +777,19 @@ OMAPLFB_BOOL OMAPLFBManualSync(OMAPLFB_DEVINFO *psDevInfo)
                int res = psDSSDrv->sync(psDSSDev);
                if (res != 0)
                {
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: Sync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: Sync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                        return OMAPLFB_FALSE;
                }
        }
+
        return OMAPLFB_TRUE;
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 }
 
+/*
+ * If the screen is manual or auto update mode, wait for the screen to
+ * update.
+ */
 OMAPLFB_BOOL OMAPLFBCheckModeAndSync(OMAPLFB_DEVINFO *psDevInfo)
 {
        OMAPLFB_UPDATE_MODE eMode = OMAPLFBGetUpdateMode(psDevInfo);
@@ -414,6 +806,7 @@ OMAPLFB_BOOL OMAPLFBCheckModeAndSync(OMAPLFB_DEVINFO *psDevInfo)
        return OMAPLFB_TRUE;
 }
 
+/* Linux Framebuffer event notification handler */
 static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
                              unsigned long event, void *data)
 {
@@ -422,7 +815,7 @@ static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
        struct fb_info *psFBInfo = psFBEvent->info;
        OMAPLFB_BOOL bBlanked;
 
-       
+       /* Only interested in blanking events */
        if (event != FB_EVENT_BLANK)
        {
                return 0;
@@ -459,46 +852,32 @@ static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
        return 0;
 }
 
+/* Unblank the screen */
 OMAPLFB_ERROR OMAPLFBUnblankDisplay(OMAPLFB_DEVINFO *psDevInfo)
 {
-#ifdef FBDEV_PRESENT
        int res;
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-       acquire_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_LOCK();
        res = fb_blank(psDevInfo->psLINFBInfo, 0);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-       release_console_sem();
-#endif
+       OMAPLFB_CONSOLE_UNLOCK();
        if (res != 0 && res != -EINVAL)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_blank failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                return (OMAPLFB_ERROR_GENERIC);
        }
-#endif
+
        return (OMAPLFB_OK);
 }
 
 #ifdef CONFIG_HAS_EARLYSUSPEND
 
+/* Blank the screen */
 static void OMAPLFBBlankDisplay(OMAPLFB_DEVINFO *psDevInfo)
 {
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-       acquire_console_sem();
-#endif
+       OMAPLFB_CONSOLE_LOCK();
        fb_blank(psDevInfo->psLINFBInfo, 1);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-       release_console_sem();
-#endif
+       OMAPLFB_CONSOLE_UNLOCK();
 }
 
 static void OMAPLFBEarlySuspendHandler(struct early_suspend *h)
@@ -535,14 +914,15 @@ static void OMAPLFBEarlyResumeHandler(struct early_suspend *h)
        }
 }
 
-#endif 
+#endif /* CONFIG_HAS_EARLYSUSPEND */
 
+/* Set up Linux Framebuffer event notification */
 OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 {
        int                res;
        OMAPLFB_ERROR         eError;
 
-       
+       /* Set up Linux Framebuffer event notification */
        memset(&psDevInfo->sLINNotifBlock, 0, sizeof(psDevInfo->sLINNotifBlock));
 
        psDevInfo->sLINNotifBlock.notifier_call = OMAPLFBFrameBufferEvents;
@@ -553,7 +933,7 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        res = fb_register_client(&psDevInfo->sLINNotifBlock);
        if (res != 0)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_register_client failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
 
                return (OMAPLFB_ERROR_GENERIC);
@@ -562,7 +942,7 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        eError = OMAPLFBUnblankDisplay(psDevInfo);
        if (eError != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: UnblankDisplay failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eError);
                return eError;
        }
@@ -570,13 +950,14 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 #ifdef CONFIG_HAS_EARLYSUSPEND
        psDevInfo->sEarlySuspend.suspend = OMAPLFBEarlySuspendHandler;
        psDevInfo->sEarlySuspend.resume = OMAPLFBEarlyResumeHandler;
-       psDevInfo->sEarlySuspend.level = EARLY_SUSPEND_LEVEL_BLANK_SCREEN;
+       psDevInfo->sEarlySuspend.level = EARLY_SUSPEND_LEVEL_DISABLE_FB + 1;
        register_early_suspend(&psDevInfo->sEarlySuspend);
 #endif
 
        return (OMAPLFB_OK);
 }
 
+/* Disable Linux Framebuffer event notification */
 OMAPLFB_ERROR OMAPLFBDisableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 {
        int res;
@@ -585,11 +966,11 @@ OMAPLFB_ERROR OMAPLFBDisableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        unregister_early_suspend(&psDevInfo->sEarlySuspend);
 #endif
 
-       
+       /* Unregister for Framebuffer events */
        res = fb_unregister_client(&psDevInfo->sLINNotifBlock);
        if (res != 0)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_unregister_client failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                return (OMAPLFB_ERROR_GENERIC);
        }
@@ -615,13 +996,13 @@ static OMAPLFB_DEVINFO *OMAPLFBPVRDevIDToDevInfo(unsigned uiPVRDevID)
                }
        }
 
-       printk(KERN_WARNING DRIVER_PREFIX
+       printk(KERN_ERR DRIVER_PREFIX
                ": %s: PVR Device %u: Couldn't find device\n", __FUNCTION__, uiPVRDevID);
 
        return NULL;
 }
 
-int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg, struct drm_file unref__ *pFile)
+int PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Ioctl)(struct drm_device unref__ *dev, void *arg, struct drm_file unref__ *pFile)
 {
        uint32_t *puiArgs;
        uint32_t uiCmd;
@@ -700,7 +1081,7 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
                                                pszMode = "(Unknown Mode)";
                                                break;
                                }
-                               printk (KERN_WARNING DRIVER_PREFIX ": %s: PVR Device %u: Display %s\n",
+                               printk(KERN_WARNING DRIVER_PREFIX ": %s: PVR Device %u: Display %s\n",
                                __FUNCTION__, uiPVRDevID, pszMode);
                        }
 #endif
@@ -729,17 +1110,9 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
                                flush_workqueue(psDevInfo->psSwapChain->psWorkQueue);
                        }
 
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-                       console_lock();
-#else
-                       acquire_console_sem();
-#endif
+                       OMAPLFB_CONSOLE_LOCK();
                        ret = fb_blank(psDevInfo->psLINFBInfo, iFBMode);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-                       console_unlock();
-#else
-                       release_console_sem();
-#endif
+                       OMAPLFB_CONSOLE_UNLOCK();
 
                        OMAPLFBCreateSwapChainUnLock(psDevInfo);
 
@@ -756,15 +1129,17 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
 }
 #endif
 
+/* Insert the driver into the kernel */
 #if defined(SUPPORT_DRI_DRM)
-int PVR_DRM_MAKENAME(omaplfb, _Init)(struct drm_device unref__ *dev)
+int PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Init)(struct drm_device unref__ *dev)
 #else
 static int __init OMAPLFB_Init(void)
 #endif
 {
+
        if(OMAPLFBInit() != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: OMAPLFBInit failed\n", __FUNCTION__);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: OMAPLFBInit failed\n", __FUNCTION__);
                return -ENODEV;
        }
 
@@ -772,19 +1147,26 @@ static int __init OMAPLFB_Init(void)
 
 }
 
+/* Remove the driver from the kernel */
 #if defined(SUPPORT_DRI_DRM)
-void PVR_DRM_MAKENAME(omaplfb, _Cleanup)(struct drm_device unref__ *dev)
+void PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Cleanup)(struct drm_device unref__ *dev)
 #else
 static void __exit OMAPLFB_Cleanup(void)
 #endif
 {    
        if(OMAPLFBDeInit() != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: OMAPLFBDeInit failed\n", __FUNCTION__);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: OMAPLFBDeInit failed\n", __FUNCTION__);
        }
 }
 
 #if !defined(SUPPORT_DRI_DRM)
+/*
+ These macro calls define the initialisation and removal functions of the
+ driver.  Although they are prefixed `module_', they apply when compiling
+ statically as well; in both cases they define the function the kernel will
+ run to start/stop the driver.
+*/
 late_initcall(OMAPLFB_Init);
 module_exit(OMAPLFB_Cleanup);
 #endif
index 9b6d240..addbfc2 100644 (file)
@@ -1,29 +1,46 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OMAP Linux display driver shared DRM structures
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    OMAP Linux display driver DRM structures shared between
+                kernel and user space.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
 #ifndef __3RDPARTY_DC_DRM_SHARED_H__
 #define __3RDPARTY_DC_DRM_SHARED_H__
 #if defined(SUPPORT_DRI_DRM)
@@ -40,6 +57,9 @@
 #define        PVR_DRM_DISP_ARG_DEV            1
 #define        PVR_DRM_DISP_NUM_ARGS           2
 
-#endif 
-#endif 
+#endif /* defined(SUPPORT_DRI_DRM) */
+#endif /* __3RDPARTY_DC_DRM_SHARED_H__ */
 
+/******************************************************************************
+ End of file (3rdparty_dc_drm_shared.h)
+******************************************************************************/
diff --git a/services4/3rdparty/dc_ti335x_linux/Kbuild.mk b/services4/3rdparty/dc_ti335x_linux/Kbuild.mk
new file mode 100644 (file)
index 0000000..eca9351
--- /dev/null
@@ -0,0 +1,49 @@
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
+# 
+# The contents of this file are subject to the MIT license as set out below.
+# 
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+# 
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+# 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
+# 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#   
+### ###########################################################################
+
+ccflags-y += \
+       -I$(TOP)/services4/3rdparty/dc_omapfb3_linux \
+       -I$(KERNELDIR)/drivers/video/omap2 \
+       -I$(KERNELDIR)/arch/arm/plat-omap/include
+
+omaplfb-y += \
+       services4/3rdparty/dc_omapfb3_linux/omaplfb_displayclass.o \
+       services4/3rdparty/dc_omapfb3_linux/omaplfb_linux.o
diff --git a/services4/3rdparty/dc_ti335x_linux/Linux.mk b/services4/3rdparty/dc_ti335x_linux/Linux.mk
new file mode 100644 (file)
index 0000000..7574073
--- /dev/null
@@ -0,0 +1,46 @@
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
+# 
+# The contents of this file are subject to the MIT license as set out below.
+# 
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+# 
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+# 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
+# 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#   
+### ###########################################################################
+
+modules := dc_omapfb3_linux
+
+dc_omapfb3_linux_type := kernel_module
+dc_omapfb3_linux_target := omaplfb.ko
+dc_omapfb3_linux_makefile := $(THIS_DIR)/Kbuild.mk
diff --git a/services4/3rdparty/dc_ti335x_linux/kbuild/Makefile b/services4/3rdparty/dc_ti335x_linux/kbuild/Makefile
deleted file mode 100644 (file)
index f52617a..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-#
-# Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
-# 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
-# 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
-# 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
-# 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
-# 
-#
-
-MODULE         = $(DISPLAY_CONTROLLER)
-
-INCLUDES =
-
-SOURCES        =
-
-SYM_VERS_DEPS = $(EURASIAROOT)/services4/srvkm/env/linux
-
-include $(EURASIAROOT)/services4/$(DISPLAY_CONTROLLER_DIR)/makefile.linux.common
-
-include $(EURASIAROOT)/eurasiacon/build/linux/kbuild/Makefile.kbuild_subdir_common
diff --git a/services4/3rdparty/dc_ti335x_linux/makefile.linux.common b/services4/3rdparty/dc_ti335x_linux/makefile.linux.common
deleted file mode 100644 (file)
index d5b4a30..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-#
-# Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
-# 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
-# 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
-# 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
-# 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
-# 
-#
-#
-
-ifeq ($(SUPPORT_DRI_DRM),1)
-DISPLAY_CONTROLLER_SOURCES_ROOT = $(KBUILDROOT)/$(DISPLAY_CONTROLLER_DIR)
-MODULE_CFLAGS += -DPVR_DISPLAY_CONTROLLER_DRM_IOCTL
-else
-DISPLAY_CONTROLLER_SOURCES_ROOT = ..
-endif
-
-INCLUDES +=    -I$(EURASIAROOT)/include4 \
-               -I$(EURASIAROOT)/services4/include \
-               -I$(EURASIAROOT)/services4/system/$(PVR_SYSTEM) \
-               -I$(EURASIAROOT)/services4/system/include \
-               -I$(KERNELDIR)/drivers/video/omap2 \
-               -I$(KERNELDIR)/arch/arm/plat-omap/include
-
-SOURCES        +=      $(DISPLAY_CONTROLLER_SOURCES_ROOT)/omaplfb_displayclass.c \
-                       $(DISPLAY_CONTROLLER_SOURCES_ROOT)/omaplfb_linux.c
index f202e1e..c69640d 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          OMAP Linux display driver structures and prototypes
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
 #ifndef __OMAPLFB_H__
 #define __OMAPLFB_H__
 
 #include <linux/earlysuspend.h>
 #endif
 
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38))
+#define        OMAPLFB_CONSOLE_LOCK()          console_lock()
+#define        OMAPLFB_CONSOLE_UNLOCK()        console_unlock()
+#else
+#define        OMAPLFB_CONSOLE_LOCK()          acquire_console_sem()
+#define        OMAPLFB_CONSOLE_UNLOCK()        release_console_sem()
+#endif
+
 #define unref__ __attribute__ ((unused))
 
 typedef void *       OMAPLFB_HANDLE;
@@ -55,6 +78,7 @@ typedef       atomic_t        OMAPLFB_ATOMIC_BOOL;
 
 typedef atomic_t       OMAPLFB_ATOMIC_INT;
 
+/* OMAPLFB buffer structure */
 typedef struct OMAPLFB_BUFFER_TAG
 {
        struct OMAPLFB_BUFFER_TAG       *psNext;
@@ -62,11 +86,11 @@ typedef struct OMAPLFB_BUFFER_TAG
 
        struct work_struct sWork;
 
-       
+       /* Position of this buffer in the virtual framebuffer */
        unsigned long                   ulYOffset;
 
-       
-       
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
        IMG_SYS_PHYADDR                 sSysAddr;
        IMG_CPU_VIRTADDR                sCPUVAddr;
        PVRSRV_SYNC_DATA                *psSyncData;
@@ -75,27 +99,34 @@ typedef struct OMAPLFB_BUFFER_TAG
        unsigned long                   ulSwapInterval;
 } OMAPLFB_BUFFER;
 
+/* OMAPLFB swapchain structure */
 typedef struct OMAPLFB_SWAPCHAIN_TAG
 {
-       
+       /* Swap chain ID */
        unsigned int                    uiSwapChainID;
 
-       
+       /* number of buffers in swapchain */
        unsigned long                   ulBufferCount;
 
-       
+       /* list of buffers in the swapchain */
        OMAPLFB_BUFFER                  *psBuffer;
 
-       
+       /* Swap chain work queue */
        struct workqueue_struct         *psWorkQueue;
 
-       
+       /*
+        * Set if we didn't manage to wait for VSync on last swap,
+        * or if we think we need to wait for VSync on the next flip.
+        * The flag helps to avoid jitter when the screen is
+        * unblanked, by forcing an extended wait for VSync before
+        * attempting the next flip.
+        */
        OMAPLFB_BOOL                    bNotVSynced;
 
-       
+       /* Previous number of blank events */
        int                             iBlankEvents;
 
-       
+       /* Framebuffer Device ID for messages (e.g. printk) */
        unsigned int                    uiFBDevID;
 } OMAPLFB_SWAPCHAIN;
 
@@ -110,75 +141,83 @@ typedef struct OMAPLFB_FBINFO_TAG
        unsigned long       ulPhysicalWidthmm;
        unsigned long       ulPhysicalHeightmm;
 
-       
-       
-       IMG_SYS_PHYADDR     sSysAddr;
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
+       IMG_SYS_PHYADDR     sSysAddr;//system physical address
        IMG_CPU_VIRTADDR    sCPUVAddr;
 
-       
+       /* pixelformat of system/primary surface */
        PVRSRV_PIXEL_FORMAT ePixelFormat;
-}OMAPLFB_FBINFO;
 
+#if defined(CONFIG_DSSCOMP)
+       OMAPLFB_BOOL            bIs2D;
+       IMG_SYS_PHYADDR         *psPageList;
+       struct ion_handle       *psIONHandle;
+       IMG_UINT32                      uiBytesPerPixel;
+#endif
+} OMAPLFB_FBINFO;
+
+/* kernel device information structure */
 typedef struct OMAPLFB_DEVINFO_TAG
 {
-       
+       /* Framebuffer Device ID */
        unsigned int            uiFBDevID;
 
-       
+       /* PVR Device ID */
        unsigned int            uiPVRDevID;
 
-       
+       /* Swapchain create/destroy mutex */
        struct mutex            sCreateSwapChainMutex;
 
-       
+       /* system surface info */
        OMAPLFB_BUFFER          sSystemBuffer;
 
-       
+       /* jump table into PVR services */
        PVRSRV_DC_DISP2SRV_KMJTABLE     sPVRJTable;
        
-       
+       /* jump table into DC */
        PVRSRV_DC_SRV2DISP_KMJTABLE     sDCJTable;
 
-       
+       /* fb info structure */
        OMAPLFB_FBINFO          sFBInfo;
 
-       
+       /* Only one swapchain supported by this device so hang it here */
        OMAPLFB_SWAPCHAIN      *psSwapChain;
 
-       
+       /* Swap chain ID */
        unsigned int            uiSwapChainID;
 
-       
+       /* True if PVR Services is flushing its command queues */
        OMAPLFB_ATOMIC_BOOL     sFlushCommands;
 
-       
+       /* pointer to linux frame buffer information structure */
        struct fb_info         *psLINFBInfo;
 
-       
+       /* Linux Framebuffer event notification block */
        struct notifier_block   sLINNotifBlock;
 
-       
-       
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
 
-       
+       /* Address of the surface being displayed */
        IMG_DEV_VIRTADDR        sDisplayDevVAddr;
 
        DISPLAY_INFO            sDisplayInfo;
 
-       
+       /* Display format */
        DISPLAY_FORMAT          sDisplayFormat;
        
-       
+       /* Display dimensions */
        DISPLAY_DIMS            sDisplayDim;
 
-       
+       /* True if screen is blanked */
        OMAPLFB_ATOMIC_BOOL     sBlanked;
 
-       
+       /* Number of blank/unblank events */
        OMAPLFB_ATOMIC_INT      sBlankEvents;
 
 #ifdef CONFIG_HAS_EARLYSUSPEND
-       
+       /* Set by early suspend */
        OMAPLFB_ATOMIC_BOOL     sEarlySuspendFlag;
 
        struct early_suspend    sEarlySuspend;
@@ -192,8 +231,7 @@ typedef struct OMAPLFB_DEVINFO_TAG
 
 #define        OMAPLFB_PAGE_SIZE 4096
 
-//#define DEBUG
-
+/* DEBUG only printk */
 #ifdef DEBUG
 #define        DEBUG_PRINTK(x) printk x
 #else
@@ -205,6 +243,10 @@ typedef struct OMAPLFB_DEVINFO_TAG
 #define        DEVNAME DRVNAME
 #define        DRIVER_PREFIX DRVNAME
 
+/*!
+ *****************************************************************************
+ * Error values
+ *****************************************************************************/
 typedef enum _OMAPLFB_ERROR_
 {
        OMAPLFB_OK                             =  0,
@@ -234,6 +276,7 @@ typedef enum _OMAPLFB_UPDATE_MODE_
 OMAPLFB_ERROR OMAPLFBInit(void);
 OMAPLFB_ERROR OMAPLFBDeInit(void);
 
+/* OS Specific APIs */
 OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID);
 unsigned OMAPLFBMaxFBDevIDPlusOne(void);
 void *OMAPLFBAllocKernelMem(unsigned long ulSize);
@@ -267,5 +310,15 @@ void OMAPLFBAtomicIntSet(OMAPLFB_ATOMIC_INT *psAtomic, int iVal);
 int OMAPLFBAtomicIntRead(OMAPLFB_ATOMIC_INT *psAtomic);
 void OMAPLFBAtomicIntInc(OMAPLFB_ATOMIC_INT *psAtomic);
 
-#endif 
+#if defined(DEBUG)
+void OMAPLFBPrintInfo(OMAPLFB_DEVINFO *psDevInfo);
+#else
+#define        OMAPLFBPrintInfo(psDevInfo)
+#endif
+
+#endif /* __OMAPLFB_H__ */
+
+/******************************************************************************
+ End of file (omaplfb.h)
+******************************************************************************/
 
index 130c9e8..ec0b7c4 100644 (file)
@@ -1,28 +1,77 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OMAP common display driver components
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with 3rd Party display hardware.  It is NOT a specification for
+ a display controller driver, rather a specification to extend the API for a
+ pre-existing driver for the display hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying display hardware, allowing
+ the client drivers to indirectly control the display hardware and access its
+ associated memory.
+ Functions of the API include
+ - query primary surface attributes (width, height, stride, pixel format, CPU
+     physical and virtual address)
+ - swap/flip chain creation and subsequent query of surface attributes
+ - asynchronous display surface flipping, taking account of asynchronous read
+ (flip) and write (render) operations to the display surface
+
+ Note: having queried surface attributes the client drivers are able to map the
+ display memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the display surface handle.
+
+ This code is intended to be an example of how a pre-existing display driver may
+ be extended to support the 3rd Party Display interface to POWERVR Services
+ - IMG is not providing a display driver implementation.
+ **************************************************************************/
+
+/*
+ * OMAP Linux 3rd party display driver.
+ * This is based on the Generic PVR Linux Framebuffer 3rd party display
+ * driver, with OMAP specific extensions to support flipping.
+ */
 
 #include <linux/version.h>
 #include <linux/kernel.h>
 #include <linux/string.h>
 #include <linux/notifier.h>
 
+/* IMG services headers */
 #include "img_defs.h"
 #include "servicesext.h"
 #include "kerneldisplay.h"
 #include "omaplfb.h"
 
+#if defined(CONFIG_DSSCOMP)
+
+#if !defined(CONFIG_ION_OMAP)
+#error CONFIG_DSSCOMP support requires CONFIG_ION_OMAP
+#endif
+
+#include <linux/ion.h>
+#include <linux/omap_ion.h>
+
+extern struct ion_client *gpsIONClient;
+
+#include <mach/tiler.h>
+#include <video/dsscomp.h>
+#include <plat/dsscomp.h>
+
+#endif /* defined(CONFIG_DSSCOMP) */
+
 #define OMAPLFB_COMMAND_COUNT          1
 
 #define        OMAPLFB_VSYNC_SETTLE_COUNT      5
 
-#define        OMAPLFB_MAX_NUM_DEVICES         1 // FB_MAX
+//#define      OMAPLFB_MAX_NUM_DEVICES         FB_MAX
+#define        OMAPLFB_MAX_NUM_DEVICES         1
 #if (OMAPLFB_MAX_NUM_DEVICES > FB_MAX)
 #error "OMAPLFB_MAX_NUM_DEVICES must not be greater than FB_MAX"
 #endif
 
 static OMAPLFB_DEVINFO *gapsDevInfo[OMAPLFB_MAX_NUM_DEVICES];
 
+/* Top level 'hook ptr' */
 static PFN_DC_GET_PVRJTABLE gpfnGetPVRJTable = NULL;
 
+/* Round x up to a multiple of y */
 static inline unsigned long RoundUpToMultiple(unsigned long x, unsigned long y)
 {
        unsigned long div = x / y;
@@ -58,6 +128,7 @@ static inline unsigned long RoundUpToMultiple(unsigned long x, unsigned long y)
        return (div + ((rem == 0) ? 0 : 1)) * y;
 }
 
+/* Greatest common divisor of x and y */
 static unsigned long GCD(unsigned long x, unsigned long y)
 {
        while (y != 0)
@@ -70,6 +141,7 @@ static unsigned long GCD(unsigned long x, unsigned long y)
        return x;
 }
 
+/* Least common multiple of x and y */
 static unsigned long LCM(unsigned long x, unsigned long y)
 {
        unsigned long gcd = GCD(x, y);
@@ -82,6 +154,7 @@ unsigned OMAPLFBMaxFBDevIDPlusOne(void)
        return OMAPLFB_MAX_NUM_DEVICES;
 }
 
+/* Returns DevInfo pointer for a given device */
 OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID)
 {
        WARN_ON(uiFBDevID >= OMAPLFBMaxFBDevIDPlusOne());
@@ -94,6 +167,7 @@ OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID)
        return gapsDevInfo[uiFBDevID];
 }
 
+/* Sets the DevInfo pointer for a given device */
 static inline void OMAPLFBSetDevInfoPtr(unsigned uiFBDevID, OMAPLFB_DEVINFO *psDevInfo)
 {
        WARN_ON(uiFBDevID >= OMAPLFB_MAX_NUM_DEVICES);
@@ -110,6 +184,7 @@ static inline OMAPLFB_BOOL SwapChainHasChanged(OMAPLFB_DEVINFO *psDevInfo, OMAPL
                (psDevInfo->uiSwapChainID != psSwapChain->uiSwapChainID);
 }
 
+/* Don't wait for vertical sync */
 static inline OMAPLFB_BOOL DontWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
 {
        OMAPLFB_BOOL bDontWait;
@@ -126,6 +201,10 @@ static inline OMAPLFB_BOOL DontWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
        return bDontWait;
 }
 
+/*
+ * SetDCState
+ * Called from services.
+ */
 static IMG_VOID SetDCState(IMG_HANDLE hDevice, IMG_UINT32 ui32State)
 {
        OMAPLFB_DEVINFO *psDevInfo = (OMAPLFB_DEVINFO *)hDevice;
@@ -138,11 +217,18 @@ static IMG_VOID SetDCState(IMG_HANDLE hDevice, IMG_UINT32 ui32State)
                case DC_STATE_NO_FLUSH_COMMANDS:
                        OMAPLFBAtomicBoolSet(&psDevInfo->sFlushCommands, OMAPLFB_FALSE);
                        break;
+               case DC_STATE_FORCE_SWAP_TO_SYSTEM:
+                       OMAPLFBFlip(psDevInfo, &psDevInfo->sSystemBuffer);
+                       break;
                default:
                        break;
        }
 }
 
+/*
+ * OpenDCDevice
+ * Called from services.
+ */
 static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                                  IMG_HANDLE *phDevice,
                                  PVRSRV_SYNC_DATA* psSystemBufferSyncData)
@@ -167,7 +253,7 @@ static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                return PVRSRV_ERROR_INVALID_DEVICE;
        }
 
-       
+       /* store the system surface sync data */
        psDevInfo->sSystemBuffer.psSyncData = psSystemBufferSyncData;
        
        eError = OMAPLFBUnblankDisplay(psDevInfo);
@@ -178,12 +264,16 @@ static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                return PVRSRV_ERROR_UNBLANK_DISPLAY_FAILED;
        }
 
-       
+       /* return handle to the devinfo */
        *phDevice = (IMG_HANDLE)psDevInfo;
        
        return PVRSRV_OK;
 }
 
+/*
+ * CloseDCDevice
+ * Called from services.
+ */
 static PVRSRV_ERROR CloseDCDevice(IMG_HANDLE hDevice)
 {
 #if defined(SUPPORT_DRI_DRM)
@@ -197,6 +287,10 @@ static PVRSRV_ERROR CloseDCDevice(IMG_HANDLE hDevice)
        return PVRSRV_OK;
 }
 
+/*
+ * EnumDCFormats
+ * Called from services.
+ */
 static PVRSRV_ERROR EnumDCFormats(IMG_HANDLE hDevice,
                                   IMG_UINT32 *pui32NumFormats,
                                   DISPLAY_FORMAT *psFormat)
@@ -220,6 +314,10 @@ static PVRSRV_ERROR EnumDCFormats(IMG_HANDLE hDevice,
        return PVRSRV_OK;
 }
 
+/*
+ * EnumDCDims
+ * Called from services.
+ */
 static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice, 
                                DISPLAY_FORMAT *psFormat,
                                IMG_UINT32 *pui32NumDims,
@@ -236,7 +334,7 @@ static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice,
 
        *pui32NumDims = 1;
 
-       
+       /* No need to look at psFormat; there is only one */
        if(psDim)
        {
                psDim[0] = psDevInfo->sDisplayDim;
@@ -246,6 +344,10 @@ static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice,
 }
 
 
+/*
+ * GetDCSystemBuffer
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCSystemBuffer(IMG_HANDLE hDevice, IMG_HANDLE *phBuffer)
 {
        OMAPLFB_DEVINFO *psDevInfo;
@@ -263,6 +365,10 @@ static PVRSRV_ERROR GetDCSystemBuffer(IMG_HANDLE hDevice, IMG_HANDLE *phBuffer)
 }
 
 
+/*
+ * GetDCInfo
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCInfo(IMG_HANDLE hDevice, DISPLAY_INFO *psDCInfo)
 {
        OMAPLFB_DEVINFO *psDevInfo;
@@ -279,6 +385,10 @@ static PVRSRV_ERROR GetDCInfo(IMG_HANDLE hDevice, DISPLAY_INFO *psDCInfo)
        return PVRSRV_OK;
 }
 
+/*
+ * GetDCBufferAddr
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
                                     IMG_HANDLE        hBuffer, 
                                     IMG_SYS_PHYADDR   **ppsSysAddr,
@@ -323,7 +433,11 @@ static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
 
        if (ppvCpuVAddr)
        {
+#if defined(CONFIG_DSSCOMP)
+               *ppvCpuVAddr = psDevInfo->sFBInfo.bIs2D ? NULL : psSystemBuffer->sCPUVAddr;
+#else
                *ppvCpuVAddr = psSystemBuffer->sCPUVAddr;
+#endif
        }
 
        if (phOSMapInfo)
@@ -333,12 +447,28 @@ static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
 
        if (pbIsContiguous)
        {
+#if defined(CONFIG_DSSCOMP)
+               *pbIsContiguous = !psDevInfo->sFBInfo.bIs2D;
+#else
                *pbIsContiguous = IMG_TRUE;
+#endif
        }
 
+#if defined(CONFIG_DSSCOMP)
+       if (psDevInfo->sFBInfo.bIs2D)
+       {
+               int i = (psSystemBuffer->sSysAddr.uiAddr - psDevInfo->sFBInfo.psPageList->uiAddr) >> PAGE_SHIFT;
+               *ppsSysAddr = psDevInfo->sFBInfo.psPageList + psDevInfo->sFBInfo.ulHeight * i;
+       }
+#endif
+
        return PVRSRV_OK;
 }
 
+/*
+ * CreateDCSwapChain
+ * Called from services.
+ */
 static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                                       IMG_UINT32 ui32Flags,
                                       DISPLAY_SURF_ATTRIBUTES *psDstSurfAttrib,
@@ -358,7 +488,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        UNREFERENCED_PARAMETER(ui32OEMFlags);
        
-       
+       /* Check parameters */
        if(!hDevice
        || !psDstSurfAttrib
        || !psSrcSurfAttrib
@@ -370,7 +500,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        psDevInfo = (OMAPLFB_DEVINFO*)hDevice;
        
-       
+       /* Do we support swap chains? */
        if (psDevInfo->sDisplayInfo.ui32MaxSwapChains == 0)
        {
                return PVRSRV_ERROR_NOT_SUPPORTED;
@@ -378,14 +508,14 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        OMAPLFBCreateSwapChainLock(psDevInfo);
 
-       
+       /* The driver only supports a single swapchain */
        if(psDevInfo->psSwapChain != NULL)
        {
                eError = PVRSRV_ERROR_FLIP_CHAIN_EXISTS;
                goto ExitUnLock;
        }
        
-       
+       /* Check the buffer count */
        if(ui32BufferCount > psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers)
        {
                eError = PVRSRV_ERROR_TOOMANYBUFFERS;
@@ -398,16 +528,23 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                goto ExitUnLock;
        }
 
-       
+       /*
+        * We will allocate the swap chain buffers at the back of the frame
+        * buffer area.  This preserves the front portion, which may be being
+        * used by other Linux Framebuffer based applications.
+        */
        ui32BuffersToSkip = psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers - ui32BufferCount;
 
-       
+       /* 
+        *      Verify the DST/SRC attributes,
+        *      SRC/DST must match the current display mode config
+       */
        if(psDstSurfAttrib->pixelformat != psDevInfo->sDisplayFormat.pixelformat
        || psDstSurfAttrib->sDims.ui32ByteStride != psDevInfo->sDisplayDim.ui32ByteStride
        || psDstSurfAttrib->sDims.ui32Width != psDevInfo->sDisplayDim.ui32Width
        || psDstSurfAttrib->sDims.ui32Height != psDevInfo->sDisplayDim.ui32Height)
        {
-               
+               /* DST doesn't match the current mode */
                eError = PVRSRV_ERROR_INVALID_PARAMS;
                goto ExitUnLock;
        }               
@@ -417,12 +554,12 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
        || psDstSurfAttrib->sDims.ui32Width != psSrcSurfAttrib->sDims.ui32Width
        || psDstSurfAttrib->sDims.ui32Height != psSrcSurfAttrib->sDims.ui32Height)
        {
-               
+               /* DST doesn't match the SRC */
                eError = PVRSRV_ERROR_INVALID_PARAMS;
                goto ExitUnLock;
        }               
 
-       
+       /* check flags if implementation requires them */
        UNREFERENCED_PARAMETER(ui32Flags);
        
 #if defined(PVR_OMAPFB3_UPDATE_MODE)
@@ -431,7 +568,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set frame buffer update mode %d\n", __FUNCTION__, psDevInfo->uiFBDevID, PVR_OMAPFB3_UPDATE_MODE);
        }
 #endif
-       
+       /* create a swapchain structure */
        psSwapChain = (OMAPLFB_SWAPCHAIN*)OMAPLFBAllocKernelMem(sizeof(OMAPLFB_SWAPCHAIN));
        if(!psSwapChain)
        {
@@ -451,20 +588,27 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
        psSwapChain->bNotVSynced = OMAPLFB_TRUE;
        psSwapChain->uiFBDevID = psDevInfo->uiFBDevID;
 
-       
+       /* Link the buffers */
        for(i=0; i<ui32BufferCount-1; i++)
        {
                psBuffer[i].psNext = &psBuffer[i+1];
        }
-       
+       /* and link last to first */
        psBuffer[i].psNext = &psBuffer[0];
 
-       
+       /* Configure the swapchain buffers */
        for(i=0; i<ui32BufferCount; i++)
        {
                IMG_UINT32 ui32SwapBuffer = i + ui32BuffersToSkip;
                IMG_UINT32 ui32BufferOffset = ui32SwapBuffer * (IMG_UINT32)psDevInfo->sFBInfo.ulRoundedBufferSize;
 
+#if defined(CONFIG_DSSCOMP)
+               if (psDevInfo->sFBInfo.bIs2D)
+               {
+                       ui32BufferOffset = 0;
+               }
+#endif /* defined(CONFIG_DSSCOMP) */
+
                psBuffer[i].psSyncData = ppsSyncData[i];
 
                psBuffer[i].sSysAddr.uiAddr = psDevInfo->sFBInfo.sSysAddr.uiAddr + ui32BufferOffset;
@@ -472,6 +616,14 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                psBuffer[i].ulYOffset = ui32BufferOffset / psDevInfo->sFBInfo.ulByteStride;
                psBuffer[i].psDevInfo = psDevInfo;
 
+#if defined(CONFIG_DSSCOMP)
+               if (psDevInfo->sFBInfo.bIs2D)
+               {
+                       psBuffer[i].sSysAddr.uiAddr += ui32SwapBuffer *
+                               ALIGN((IMG_UINT32)psDevInfo->sFBInfo.ulWidth * psDevInfo->sFBInfo.uiBytesPerPixel, PAGE_SIZE);
+               }
+#endif /* defined(CONFIG_DSSCOMP) */
+
                OMAPLFBInitBufferForSwap(&psBuffer[i]);
        }
 
@@ -517,6 +669,10 @@ ExitUnLock:
        return eError;
 }
 
+/*
+ * DestroyDCSwapChain
+ * Called from services.
+ */
 static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
        IMG_HANDLE hSwapChain)
 {
@@ -524,7 +680,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
        OMAPLFB_SWAPCHAIN *psSwapChain;
        OMAPLFB_ERROR eError;
 
-       
+       /* Check parameters */
        if(!hDevice || !hSwapChain)
        {
                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -544,7 +700,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
                goto ExitUnLock;
        }
 
-       
+       /* The swap queue is flushed before being destroyed */
        OMAPLFBDestroySwapQueue(psSwapChain);
 
        eError = OMAPLFBDisableLFBEventNotification(psDevInfo);
@@ -553,7 +709,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
                printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't disable framebuffer event notification\n", __FUNCTION__, psDevInfo->uiFBDevID);
        }
 
-       
+       /* Free resources */
        OMAPLFBFreeKernelMem(psSwapChain->psBuffer);
        OMAPLFBFreeKernelMem(psSwapChain);
 
@@ -570,6 +726,10 @@ ExitUnLock:
        return eError;
 }
 
+/*
+ * SetDCDstRect
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCDstRect(IMG_HANDLE hDevice,
        IMG_HANDLE hSwapChain,
        IMG_RECT *psRect)
@@ -578,11 +738,15 @@ static PVRSRV_ERROR SetDCDstRect(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(psRect);
 
-       
+       /* Only full display swapchains on this device */
        
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCSrcRect
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCSrcRect(IMG_HANDLE hDevice,
                                  IMG_HANDLE hSwapChain,
                                  IMG_RECT *psRect)
@@ -591,11 +755,15 @@ static PVRSRV_ERROR SetDCSrcRect(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(psRect);
 
-       
+       /* Only full display swapchains on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCDstColourKey
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCDstColourKey(IMG_HANDLE hDevice,
                                       IMG_HANDLE hSwapChain,
                                       IMG_UINT32 ui32CKColour)
@@ -604,11 +772,15 @@ static PVRSRV_ERROR SetDCDstColourKey(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(ui32CKColour);
 
-       
+       /* Don't support DST CK on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCSrcColourKey
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCSrcColourKey(IMG_HANDLE hDevice,
                                       IMG_HANDLE hSwapChain,
                                       IMG_UINT32 ui32CKColour)
@@ -617,11 +789,15 @@ static PVRSRV_ERROR SetDCSrcColourKey(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(ui32CKColour);
 
-       
+       /* Don't support SRC CK on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * GetDCBuffers
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
                                  IMG_HANDLE hSwapChain,
                                  IMG_UINT32 *pui32BufferCount,
@@ -632,7 +808,7 @@ static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
        PVRSRV_ERROR eError;
        unsigned i;
        
-       
+       /* Check parameters */
        if(!hDevice 
        || !hSwapChain
        || !pui32BufferCount
@@ -655,10 +831,10 @@ static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
                goto Exit;
        }
        
-       
+       /* Return the buffer count */
        *pui32BufferCount = (IMG_UINT32)psSwapChain->ulBufferCount;
        
-       
+       /* Return the buffers */
        for(i=0; i<psSwapChain->ulBufferCount; i++)
        {
                phBuffer[i] = (IMG_HANDLE)&psSwapChain->psBuffer[i];
@@ -672,6 +848,10 @@ Exit:
        return eError;
 }
 
+/*
+ * SwapToDCBuffer
+ * Called from services.
+ */
 static PVRSRV_ERROR SwapToDCBuffer(IMG_HANDLE hDevice,
                                    IMG_HANDLE hBuffer,
                                    IMG_UINT32 ui32SwapInterval,
@@ -686,21 +866,17 @@ static PVRSRV_ERROR SwapToDCBuffer(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(ui32ClipRectCount);
        UNREFERENCED_PARAMETER(psClipRect);
        
-       
+       /* * Nothing to do since Services common code does the work */
 
        return PVRSRV_OK;
 }
 
-static PVRSRV_ERROR SwapToDCSystem(IMG_HANDLE hDevice,
-                                   IMG_HANDLE hSwapChain)
-{
-       UNREFERENCED_PARAMETER(hDevice);
-       UNREFERENCED_PARAMETER(hSwapChain);
-       
-       
-       return PVRSRV_OK;
-}
-
+/*
+ * Called after the screen has unblanked, or after any other occasion
+ * when we didn't wait for vsync, but now need to. Not doing this after
+ * unblank leads to screen jitter on some screens.
+ * Returns true if the screen has been deemed to have settled.
+ */
 static OMAPLFB_BOOL WaitForVSyncSettle(OMAPLFB_DEVINFO *psDevInfo)
 {
                unsigned i;
@@ -715,19 +891,27 @@ static OMAPLFB_BOOL WaitForVSyncSettle(OMAPLFB_DEVINFO *psDevInfo)
                return OMAPLFB_TRUE;
 }
 
+/*
+ * Swap handler.
+ * Called from the swap chain work queue handler.
+ * There is no need to take the swap chain creation lock in here, or use
+ * some other method of stopping the swap chain from being destroyed.
+ * This is because the swap chain creation lock is taken when queueing work,
+ * and the work queue is flushed before the swap chain is destroyed.
+ */
 void OMAPLFBSwapHandler(OMAPLFB_BUFFER *psBuffer)
 {
        OMAPLFB_DEVINFO *psDevInfo = psBuffer->psDevInfo;
        OMAPLFB_SWAPCHAIN *psSwapChain = psDevInfo->psSwapChain;
        OMAPLFB_BOOL bPreviouslyNotVSynced;
-#if 1
+
 #if defined(SUPPORT_DRI_DRM)
        if (!OMAPLFBAtomicBoolRead(&psDevInfo->sLeaveVT))
 #endif
        {
                OMAPLFBFlip(psDevInfo, psBuffer);
        }
-#endif
+
        bPreviouslyNotVSynced = psSwapChain->bNotVSynced;
        psSwapChain->bNotVSynced = OMAPLFB_TRUE;
 
@@ -764,72 +948,248 @@ void OMAPLFBSwapHandler(OMAPLFB_BUFFER *psBuffer)
                }
        }
 
-#if 0
-#if defined(SUPPORT_DRI_DRM)
-        if (!OMAPLFBAtomicBoolRead(&psDevInfo->sLeaveVT))
-#endif
-        {
-                OMAPLFBFlip(psDevInfo, psBuffer);
-        }
-#endif
-
        psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete((IMG_HANDLE)psBuffer->hCmdComplete, IMG_TRUE);
 }
 
+/* Triggered by PVRSRVSwapToDCBuffer */
+static IMG_BOOL ProcessFlipV1(IMG_HANDLE hCmdCookie,
+                                                         OMAPLFB_DEVINFO *psDevInfo,
+                                                         OMAPLFB_SWAPCHAIN *psSwapChain,
+                                                         OMAPLFB_BUFFER *psBuffer,
+                                                         unsigned long ulSwapInterval)
+{
+       OMAPLFBCreateSwapChainLock(psDevInfo);
+
+       /* The swap chain has been destroyed */
+       if (SwapChainHasChanged(psDevInfo, psSwapChain))
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX
+                       ": %s: Device %u (PVR Device ID %u): The swap chain has been destroyed\n",
+                       __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
+       }
+       else
+       {
+               psBuffer->hCmdComplete = (OMAPLFB_HANDLE)hCmdCookie;
+               psBuffer->ulSwapInterval = ulSwapInterval;
+#if defined(CONFIG_DSSCOMP)
+               if (is_tiler_addr(psBuffer->sSysAddr.uiAddr))
+               {
+                       IMG_UINT32 w = psBuffer->psDevInfo->sDisplayDim.ui32Width;
+                       IMG_UINT32 h = psBuffer->psDevInfo->sDisplayDim.ui32Height;
+                       struct dsscomp_setup_dispc_data comp = {
+                               .num_mgrs = 1,
+                               .mgrs[0].alpha_blending = 1,
+                               .num_ovls = 1,
+                               .ovls[0].cfg =
+                               {
+                                       .width = w,
+                                       .win.w = w,
+                                       .crop.w = w,
+                                       .height = h,
+                                       .win.h = h,
+                                       .crop.h = h,
+                                       .stride = psBuffer->psDevInfo->sDisplayDim.ui32ByteStride,
+                                       .color_mode = OMAP_DSS_COLOR_ARGB32,
+                                       .enabled = 1,
+                                       .global_alpha = 255,
+                               },
+                               .mode = DSSCOMP_SETUP_DISPLAY,
+                       };
+                       struct tiler_pa_info *pas[1] = { NULL };
+                       comp.ovls[0].ba = (u32) psBuffer->sSysAddr.uiAddr;
+                       dsscomp_gralloc_queue(&comp, pas, true,
+                                                                 (void *) psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete,
+                                                                 (void *) psBuffer->hCmdComplete);
+               }
+               else
+#endif /* defined(CONFIG_DSSCOMP) */
+               {
+                       OMAPLFBQueueBufferForSwap(psSwapChain, psBuffer);
+               }
+       }
+
+       OMAPLFBCreateSwapChainUnLock(psDevInfo);
+
+       return IMG_TRUE;
+}
+
+#if defined(CONFIG_DSSCOMP)
+
+/* Triggered by PVRSRVSwapToDCBuffer2 */
+static IMG_BOOL ProcessFlipV2(IMG_HANDLE hCmdCookie,
+                                                         OMAPLFB_DEVINFO *psDevInfo,
+                                                         PDC_MEM_INFO *ppsMemInfos,
+                                                         IMG_UINT32 ui32NumMemInfos,
+                                                         struct dsscomp_setup_dispc_data *psDssData,
+                                                         IMG_UINT32 ui32DssDataLength)
+{
+       struct tiler_pa_info *apsTilerPAs[5];
+       IMG_UINT32 i, k;
+
+       if(ui32DssDataLength != sizeof(*psDssData))
+       {
+               WARN(1, "invalid size of private data (%d vs %d)",
+                        ui32DssDataLength, sizeof(*psDssData));
+               return IMG_FALSE;
+       }
+
+       if(psDssData->num_ovls == 0 || ui32NumMemInfos == 0)
+       {
+               WARN(1, "must have at least one layer");
+               return IMG_FALSE;
+       }
+
+       for(i = k = 0; i < ui32NumMemInfos && k < ARRAY_SIZE(apsTilerPAs); i++, k++)
+       {
+               struct tiler_pa_info *psTilerInfo;
+               IMG_CPU_VIRTADDR virtAddr;
+               IMG_CPU_PHYADDR phyAddr;
+               IMG_UINT32 ui32NumPages;
+               IMG_SIZE_T uByteSize;
+               int j;
+
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetByteSize(ppsMemInfos[i], &uByteSize);
+               ui32NumPages = (uByteSize + PAGE_SIZE - 1) >> PAGE_SHIFT;
+
+               apsTilerPAs[k] = NULL;
+
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], 0, &phyAddr);
+
+               /* NV12 buffers are already mapped to tiler */
+               if(psDssData->ovls[k].cfg.color_mode == OMAP_DSS_COLOR_NV12)
+               {
+                       psDssData->ovls[k].ba = (u32)phyAddr.uiAddr;
+
+                       psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], (uByteSize * 2) / 3, &phyAddr);
+                       psDssData->ovls[k].uv = (u32)phyAddr.uiAddr;
+                       continue;
+               }
+
+               /* Other kinds of buffer may also already be mapped to tiler */
+               if(is_tiler_addr((u32)phyAddr.uiAddr))
+               {
+                       psDssData->ovls[k].ba = (u32)phyAddr.uiAddr;
+                       continue;
+               }
+
+               psTilerInfo = kzalloc(sizeof(*psTilerInfo), GFP_KERNEL);
+               if(!psTilerInfo)
+               {
+                       continue;
+               }
+
+               psTilerInfo->mem = kzalloc(sizeof(*psTilerInfo->mem) * ui32NumPages, GFP_KERNEL);
+               if(!psTilerInfo->mem)
+               {
+                       kfree(psTilerInfo);
+                       continue;
+               }
+
+               psTilerInfo->num_pg = ui32NumPages;
+               psTilerInfo->memtype = TILER_MEM_USING;
+
+               for(j = 0; j < ui32NumPages; j++)
+               {
+                       psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], j << PAGE_SHIFT, &phyAddr);
+                       psTilerInfo->mem[j] = (u32)phyAddr.uiAddr;
+               }
+
+               /* Need base address for in-page offset */
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuVAddr(ppsMemInfos[i], &virtAddr);
+               psDssData->ovls[k].ba = (u32)virtAddr;
+               apsTilerPAs[k] = psTilerInfo;
+       }
+
+       /* Set up cloned layer addresses (but don't duplicate tiler_pas) */
+       for(i = k; i < psDssData->num_ovls && i < ARRAY_SIZE(apsTilerPAs); i++)
+       {
+               unsigned int ix = psDssData->ovls[i].ba;
+               if(ix >= ARRAY_SIZE(apsTilerPAs))
+               {
+                       WARN(1, "Invalid clone layer (%u); skipping all cloned layers", ix);
+                       psDssData->num_ovls = k;
+                       break;
+               }
+               apsTilerPAs[i] = apsTilerPAs[ix];
+               psDssData->ovls[i].ba = psDssData->ovls[ix].ba;
+               psDssData->ovls[i].uv = psDssData->ovls[ix].uv;
+       }
+
+       dsscomp_gralloc_queue(psDssData, apsTilerPAs, false,
+                                                 (void *)psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete,
+                                                 (void *)hCmdCookie);
+
+       for(i = 0; i < k; i++)
+       {
+               tiler_pa_free(apsTilerPAs[i]);
+       }
+
+       return IMG_TRUE;
+}
+
+#endif /* defined(CONFIG_DSSCOMP) */
+
+/* Command processing flip handler function.  Called from services. */
 static IMG_BOOL ProcessFlip(IMG_HANDLE  hCmdCookie,
                             IMG_UINT32  ui32DataSize,
                             IMG_VOID   *pvData)
 {
        DISPLAYCLASS_FLIP_COMMAND *psFlipCmd;
        OMAPLFB_DEVINFO *psDevInfo;
-       OMAPLFB_BUFFER *psBuffer;
-       OMAPLFB_SWAPCHAIN *psSwapChain;
 
-       
+       /* Check parameters  */
        if(!hCmdCookie || !pvData)
        {
                return IMG_FALSE;
        }
 
-       
+       /* Validate data packet  */
        psFlipCmd = (DISPLAYCLASS_FLIP_COMMAND*)pvData;
 
-       if (psFlipCmd == IMG_NULL || sizeof(DISPLAYCLASS_FLIP_COMMAND) != ui32DataSize)
+       if (psFlipCmd == IMG_NULL)
        {
                return IMG_FALSE;
        }
 
-       
        psDevInfo = (OMAPLFB_DEVINFO*)psFlipCmd->hExtDevice;
-       psBuffer = (OMAPLFB_BUFFER*)psFlipCmd->hExtBuffer;
-       psSwapChain = (OMAPLFB_SWAPCHAIN*) psFlipCmd->hExtSwapChain;
-
-       OMAPLFBCreateSwapChainLock(psDevInfo);
 
-       if (SwapChainHasChanged(psDevInfo, psSwapChain))
+       if(psFlipCmd->hExtBuffer)
        {
-               
-               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX
-                       ": %s: Device %u (PVR Device ID %u): The swap chain has been destroyed\n",
-                       __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
+               return ProcessFlipV1(hCmdCookie,
+                                                        psDevInfo,
+                                                        psFlipCmd->hExtSwapChain,
+                                                        psFlipCmd->hExtBuffer,
+                                                        psFlipCmd->ui32SwapInterval);
        }
        else
        {
-               psBuffer->hCmdComplete = (OMAPLFB_HANDLE)hCmdCookie;
-               psBuffer->ulSwapInterval = (unsigned long)psFlipCmd->ui32SwapInterval;
-#if defined(NO_HARDWARE)
-                psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete((IMG_HANDLE)psBuffer->hCmdComplete, IMG_FALSE);
+#if defined(CONFIG_DSSCOMP)
+               DISPLAYCLASS_FLIP_COMMAND2 *psFlipCmd2;
+               psFlipCmd2 = (DISPLAYCLASS_FLIP_COMMAND2 *)pvData;
+               return ProcessFlipV2(hCmdCookie,
+                                                        psDevInfo,
+                                                        psFlipCmd2->ppsMemInfos,
+                                                        psFlipCmd2->ui32NumMemInfos,
+                                                        psFlipCmd2->pvPrivData,
+                                                        psFlipCmd2->ui32PrivDataLength);
 #else
-               OMAPLFBQueueBufferForSwap(psSwapChain, psBuffer);
+               BUG();
 #endif
        }
+}
 
-       OMAPLFBCreateSwapChainUnLock(psDevInfo);
+/*!
+******************************************************************************
 
-       return IMG_TRUE;
-}
+ @Function     OMAPLFBInitFBDev
+ @Description specifies devices in the systems memory map
+ @Input    psSysData - sys data
 
+ @Return   OMAPLFB_ERROR  :
 
+******************************************************************************/
 static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
 {
        struct fb_info *psLINFBInfo;
@@ -839,11 +1199,8 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        unsigned long FBSize;
        unsigned long ulLCM;
        unsigned uiFBDevID = psDevInfo->uiFBDevID;
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_lock();
-#else
-       acquire_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_LOCK();
 
        psLINFBInfo = registered_fb[uiFBDevID];
        if (psLINFBInfo == NULL)
@@ -856,7 +1213,10 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
                                        psLINFBInfo->screen_size :
                                        psLINFBInfo->fix.smem_len;
 
-       
+       /*
+        * Try and filter out invalid FB info structures (a problem
+        * seen on some OMAP3 systems).
+        */
        if (FBSize == 0 || psLINFBInfo->fix.line_length == 0)
        {
                eError = OMAPLFB_ERROR_INVALID_DEVICE;
@@ -918,7 +1278,87 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
                        ": Device %u: LCM of stride and page size: %lu\n",
                        psDevInfo->uiFBDevID, ulLCM));
 
-       
+       /* Additional implementation specific information */
+       OMAPLFBPrintInfo(psDevInfo);
+
+#if defined(CONFIG_DSSCOMP)
+       {
+               /* for some reason we need at least 3 buffers in the swap chain */
+               int n = FBSize / RoundUpToMultiple(psLINFBInfo->fix.line_length * psLINFBInfo->var.yres, ulLCM);
+               int res;
+               int i, x, y, w;
+               ion_phys_addr_t phys;
+               size_t size;
+               struct tiler_view_t view;
+
+               struct omap_ion_tiler_alloc_data sAllocData =
+               {
+                       /* TILER will align width to 128-bytes */
+                       /* however, SGX must have full page width */
+                       .w = ALIGN(psLINFBInfo->var.xres, PAGE_SIZE / (psLINFBInfo->var.bits_per_pixel / 8)),
+                       .h = psLINFBInfo->var.yres,
+                       .fmt = psLINFBInfo->var.bits_per_pixel == 16 ? TILER_PIXEL_FMT_16BIT : TILER_PIXEL_FMT_32BIT,
+                       .flags = 0,
+               };
+
+               printk(KERN_DEBUG DRIVER_PREFIX
+                          " %s: Device %u: Requesting %d TILER 2D framebuffers\n",
+                          __FUNCTION__, uiFBDevID, n);
+
+               /* INTEGRATION_POINT: limit to MAX 3 FBs to save TILER container space */
+               if (n > 3)
+                       n = 3;
+
+               sAllocData.w *= n;
+
+               psPVRFBInfo->uiBytesPerPixel = psLINFBInfo->var.bits_per_pixel >> 3;
+               psPVRFBInfo->bIs2D = OMAPLFB_TRUE;
+
+               res = omap_ion_tiler_alloc(gpsIONClient, &sAllocData);
+               psPVRFBInfo->psIONHandle = sAllocData.handle;
+               if (res < 0)
+               {
+                       printk(KERN_ERR DRIVER_PREFIX
+                                  " %s: Device %u: Could not allocate 2D framebuffer(%d)\n",
+                                  __FUNCTION__, uiFBDevID, res);
+                       goto ErrorModPut;
+               }
+
+               psLINFBInfo->fix.smem_start = ion_phys(gpsIONClient, sAllocData.handle, &phys, &size);
+
+               psPVRFBInfo->sSysAddr.uiAddr = phys;
+               psPVRFBInfo->sCPUVAddr = 0;
+               psPVRFBInfo->ulWidth = psLINFBInfo->var.xres;
+               psPVRFBInfo->ulHeight = psLINFBInfo->var.yres;
+
+               psPVRFBInfo->ulByteStride = PAGE_ALIGN(psPVRFBInfo->ulWidth * psPVRFBInfo->uiBytesPerPixel);
+               w = psPVRFBInfo->ulByteStride >> PAGE_SHIFT;
+               /* this is an "effective" FB size to get correct number of buffers */
+               psPVRFBInfo->ulFBSize = sAllocData.h * n * psPVRFBInfo->ulByteStride;
+               psPVRFBInfo->psPageList = kzalloc(w * n * psPVRFBInfo->ulHeight * sizeof(*psPVRFBInfo->psPageList), GFP_KERNEL);
+               if (!psPVRFBInfo->psPageList)
+               {
+                       printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Could not allocate page list\n", __FUNCTION__, psDevInfo->uiFBDevID);
+                       ion_free(gpsIONClient, sAllocData.handle);
+                       goto ErrorModPut;
+               }
+
+               tilview_create(&view, phys, psDevInfo->sFBInfo.ulWidth, psDevInfo->sFBInfo.ulHeight);
+               for(i = 0; i < n; i++)
+               {
+                       for(y = 0; y < psDevInfo->sFBInfo.ulHeight; y++)
+                       {
+                               for(x = 0; x < w; x++)
+                               {
+                                       psPVRFBInfo->psPageList[i * psDevInfo->sFBInfo.ulHeight * w + y * w + x].uiAddr =
+                                       phys + view.v_inc * y + ((x + i * w) << PAGE_SHIFT);
+                               }
+                       }
+               }
+       }
+#else /* defined(CONFIG_DSSCOMP) */
+       /* System Surface */
        psPVRFBInfo->sSysAddr.uiAddr = psLINFBInfo->fix.smem_start;
        psPVRFBInfo->sCPUVAddr = psLINFBInfo->screen_base;
 
@@ -926,8 +1366,15 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        psPVRFBInfo->ulHeight = psLINFBInfo->var.yres;
        psPVRFBInfo->ulByteStride =  psLINFBInfo->fix.line_length;
        psPVRFBInfo->ulFBSize = FBSize;
+#endif /* defined(CONFIG_DSSCOMP) */
+
        psPVRFBInfo->ulBufferSize = psPVRFBInfo->ulHeight * psPVRFBInfo->ulByteStride;
-       
+
+       /* Round the buffer size up to a multiple of the number of pages
+        * and the byte stride.
+        * This is used internally, to ensure buffers start on page
+        * boundaries, for the benefit of PVR Services.
+        */
        psPVRFBInfo->ulRoundedBufferSize = RoundUpToMultiple(psPVRFBInfo->ulBufferSize, ulLCM);
 
        if(psLINFBInfo->var.bits_per_pixel == 16)
@@ -938,7 +1385,7 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
                        (psLINFBInfo->var.red.offset == 11) &&
                        (psLINFBInfo->var.green.offset == 5) && 
                        (psLINFBInfo->var.blue.offset == 0) && 
-                       (psLINFBInfo->var.red.msb_right == 0)) 
+                       (psLINFBInfo->var.red.msb_right == 0))
                {
                        psPVRFBInfo->ePixelFormat = PVRSRV_PIXEL_FORMAT_RGB565;
                }
@@ -955,7 +1402,7 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
                        (psLINFBInfo->var.red.offset == 16) &&
                        (psLINFBInfo->var.green.offset == 8) && 
                        (psLINFBInfo->var.blue.offset == 0) && 
-                       (psLINFBInfo->var.red.msb_right == 0)) 
+                       (psLINFBInfo->var.red.msb_right == 0))
                {
                        psPVRFBInfo->ePixelFormat = PVRSRV_PIXEL_FORMAT_ARGB8888;
                }
@@ -975,7 +1422,7 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        psDevInfo->sFBInfo.ulPhysicalHeightmm =
                ((int)psLINFBInfo->var.height > 0) ? psLINFBInfo->var.height : 54;
 
-       
+       /* System Surface */
        psDevInfo->sFBInfo.sSysAddr.uiAddr = psPVRFBInfo->sSysAddr.uiAddr;
        psDevInfo->sFBInfo.sCPUVAddr = psPVRFBInfo->sCPUVAddr;
 
@@ -985,11 +1432,7 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
 ErrorModPut:
        module_put(psLINFBOwner);
 ErrorRelSem:
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_unlock();
-#else
-       release_console_sem();
-#endif
+       OMAPLFB_CONSOLE_UNLOCK();
 
        return eError;
 }
@@ -999,11 +1442,19 @@ static void OMAPLFBDeInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        struct fb_info *psLINFBInfo = psDevInfo->psLINFBInfo;
        struct module *psLINFBOwner;
 
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_lock();
-#else
-       acquire_console_sem();
-#endif
+       OMAPLFB_CONSOLE_LOCK();
+
+#if defined(CONFIG_DSSCOMP)
+       {
+               OMAPLFB_FBINFO *psPVRFBInfo = &psDevInfo->sFBInfo;
+               kfree(psPVRFBInfo->psPageList);
+               if (psPVRFBInfo->psIONHandle)
+               {
+                       ion_free(gpsIONClient, psPVRFBInfo->psIONHandle);
+               }
+       }
+#endif /* defined(CONFIG_DSSCOMP) */
+
        psLINFBOwner = psLINFBInfo->fbops->owner;
 
        if (psLINFBInfo->fbops->fb_release != NULL) 
@@ -1012,11 +1463,8 @@ static void OMAPLFBDeInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        }
 
        module_put(psLINFBOwner);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-       release_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_UNLOCK();
 }
 
 static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
@@ -1025,7 +1473,7 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
        IMG_UINT32              aui32SyncCountList[OMAPLFB_COMMAND_COUNT][2];
        OMAPLFB_DEVINFO         *psDevInfo = NULL;
 
-       
+       /* Allocate device info. structure */
        psDevInfo = (OMAPLFB_DEVINFO *)OMAPLFBAllocKernelMem(sizeof(OMAPLFB_DEVINFO));
 
        if(psDevInfo == NULL)
@@ -1036,21 +1484,26 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                goto ErrorExit;
        }
 
-       
+       /* Any fields not set will be zero */
        memset(psDevInfo, 0, sizeof(OMAPLFB_DEVINFO));
 
        psDevInfo->uiFBDevID = uiFBDevID;
 
-       
+       /* Get the kernel services function table */
        if(!(*gpfnGetPVRJTable)(&psDevInfo->sPVRJTable))
        {
                goto ErrorFreeDevInfo;
        }
 #ifdef FBDEV_PRESENT
-       
+       /* Save private fbdev information structure in the dev. info. */
        if(OMAPLFBInitFBDev(psDevInfo) != OMAPLFB_OK)
        {
-               
+               /*
+                * Leave it to OMAPLFBInitFBDev to print an error message, if
+                * required.  The function may have failed because
+                * there is no Linux framebuffer device corresponding
+                * to the device ID.
+                */
                goto ErrorFreeDevInfo;
        }
 
@@ -1075,15 +1528,14 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                ": Device %u: Maximum number of swap chain buffers: %u\n",
                psDevInfo->uiFBDevID, psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers));
 
-               
-       
+       /* Setup system buffer */
        psDevInfo->sSystemBuffer.sSysAddr = psDevInfo->sFBInfo.sSysAddr;
        psDevInfo->sSystemBuffer.sCPUVAddr = psDevInfo->sFBInfo.sCPUVAddr;
        psDevInfo->sSystemBuffer.psDevInfo = psDevInfo;
 
        OMAPLFBInitBufferForSwap(&psDevInfo->sSystemBuffer);
 #else
-                psDevInfo->sSystemBuffer.sCPUVAddr = 0x100;
+psDevInfo->sSystemBuffer.sCPUVAddr = 0x100;
 //                psDevInfo->sSystemBuffer.ulBufferSize = 600*3200;
 
                 psDevInfo->sDisplayFormat.pixelformat = 20;
@@ -1095,6 +1547,9 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
 #endif
 
 
+       /*
+               Setup the DC Jtable so SRVKM can call into this driver
+       */
        psDevInfo->sDCJTable.ui32TableSize = sizeof(PVRSRV_DC_SRV2DISP_KMJTABLE);
        psDevInfo->sDCJTable.pfnOpenDCDevice = OpenDCDevice;
        psDevInfo->sDCJTable.pfnCloseDCDevice = CloseDCDevice;
@@ -1111,10 +1566,9 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
        psDevInfo->sDCJTable.pfnSetDCSrcColourKey = SetDCSrcColourKey;
        psDevInfo->sDCJTable.pfnGetDCBuffers = GetDCBuffers;
        psDevInfo->sDCJTable.pfnSwapToDCBuffer = SwapToDCBuffer;
-       psDevInfo->sDCJTable.pfnSwapToDCSystem = SwapToDCSystem;
        psDevInfo->sDCJTable.pfnSetDCState = SetDCState;
 
-       
+       /* Register device with services and retrieve device index */
        if(psDevInfo->sPVRJTable.pfnPVRSRVRegisterDCDevice(
                &psDevInfo->sDCJTable,
                &psDevInfo->uiPVRDevID) != PVRSRV_OK)
@@ -1128,17 +1582,18 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                ": Device %u: PVR Device ID: %u\n",
                psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
        
-       
+       /* Setup private command processing function table ... */
        pfnCmdProcList[DC_FLIP_COMMAND] = ProcessFlip;
 
-       
-       aui32SyncCountList[DC_FLIP_COMMAND][0] = 0; 
-       aui32SyncCountList[DC_FLIP_COMMAND][1] = 2; 
-
-       
-
-
+       /* ... and associated sync count(s) */
+       aui32SyncCountList[DC_FLIP_COMMAND][0] = 0; /* writes */
+       aui32SyncCountList[DC_FLIP_COMMAND][1] = 10; /* reads */
 
+       /*
+               Register private command processing functions with
+               the Command Queue Manager and setup the general
+               command complete function in the devinfo.
+       */
        if (psDevInfo->sPVRJTable.pfnPVRSRVRegisterCmdProcList(psDevInfo->uiPVRDevID,
                                                                                                                        &pfnCmdProcList[0],
                                                                                                                        aui32SyncCountList,
@@ -1183,14 +1638,18 @@ OMAPLFB_ERROR OMAPLFBInit(void)
                return OMAPLFB_ERROR_INIT_FAILURE;
        }
 
-       
+       /*
+        * We search for frame buffer devices backwards, as the last device
+        * registered with PVR Services will be the first device enumerated
+        * by PVR Services.
+        */
        for(i = uiMaxFBDevIDPlusOne; i-- != 0;)
        {
                OMAPLFB_DEVINFO *psDevInfo = OMAPLFBInitDev(i);
 
                if (psDevInfo != NULL)
                {
-                       
+                       /* Set the top-level anchor */
                        OMAPLFBSetDevInfoPtr(psDevInfo->uiFBDevID, psDevInfo);
                        uiDevicesFound++;
                }
@@ -1199,6 +1658,10 @@ OMAPLFB_ERROR OMAPLFBInit(void)
        return (uiDevicesFound != 0) ? OMAPLFB_OK : OMAPLFB_ERROR_INIT_FAILURE;
 }
 
+/*
+ *     OMAPLFBDeInitDev
+ *     DeInitialises one device
+ */
 static OMAPLFB_BOOL OMAPLFBDeInitDev(OMAPLFB_DEVINFO *psDevInfo)
 {
        PVRSRV_DC_DISP2SRV_KMJTABLE *psPVRJTable = &psDevInfo->sPVRJTable;
@@ -1223,24 +1686,31 @@ static OMAPLFB_BOOL OMAPLFBDeInitDev(OMAPLFB_DEVINFO *psDevInfo)
                return OMAPLFB_FALSE;
        }
 
-       
+       /*
+        * Remove display class device from kernel services device
+        * register.
+        */
        if (psPVRJTable->pfnPVRSRVRemoveDCDevice(psDevInfo->uiPVRDevID) != PVRSRV_OK)
        {
                printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: PVR Device %u: Couldn't remove device from PVR Services\n", __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID);
                return OMAPLFB_FALSE;
        }
-#ifdef FBDEV_PRESENT   
+       
        OMAPLFBDeInitFBDev(psDevInfo);
-#endif
+
        OMAPLFBSetDevInfoPtr(psDevInfo->uiFBDevID, NULL);
 
-       
+       /* De-allocate data structure */
        OMAPLFBFreeKernelMem(psDevInfo);
 
        return OMAPLFB_TRUE;
 }
 
+/*
+ *     OMAPLFBDeInit
+ *     Deinitialises the display class device component of the FBDev
+ */
 OMAPLFB_ERROR OMAPLFBDeInit(void)
 {
        unsigned uiMaxFBDevIDPlusOne = OMAPLFBMaxFBDevIDPlusOne();
@@ -1260,3 +1730,7 @@ OMAPLFB_ERROR OMAPLFBDeInit(void)
        return (bError) ? OMAPLFB_ERROR_INIT_FAILURE : OMAPLFB_OK;
 }
 
+/******************************************************************************
+ End of file (omaplfb_displayclass.c)
+******************************************************************************/
+
index c07ddf2..af2f73b 100644 (file)
@@ -1,37 +1,80 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OMAP linux display driver components
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with 3rd Party display hardware.  It is NOT a specification for
+ a display controller driver, rather a specification to extend the API for a
+ pre-existing driver for the display hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying display hardware, allowing
+ the client drivers to indirectly control the display hardware and access its
+ associated memory.
+ Functions of the API include
+ - query primary surface attributes (width, height, stride, pixel format, CPU
+     physical and virtual address)
+ - swap/flip chain creation and subsequent query of surface attributes
+ - asynchronous display surface flipping, taking account of asynchronous read
+ (flip) and write (render) operations to the display surface
+
+ Note: having queried surface attributes the client drivers are able to map the
+ display memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the display surface handle.
+
+ This code is intended to be an example of how a pre-existing display driver may
+ be extended to support the 3rd Party Display interface to POWERVR Services
+ - IMG is not providing a display driver implementation.
+ **************************************************************************/
 
 #include <linux/version.h>
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,38)
+
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,38))
 #ifndef AUTOCONF_INCLUDED
 #include <linux/config.h>
 #endif
 #endif
 
-
 #include <asm/atomic.h>
 
 #if defined(SUPPORT_DRI_DRM)
@@ -40,7 +83,6 @@
 #include <linux/module.h>
 #endif
 
-//#include <linux/time.h>
 #include <linux/kernel.h>
 #include <linux/slab.h>
 #include <linux/hardirq.h>
 #include <linux/mutex.h>
 
 #include <video/da8xx-fb.h>
-#include <plat/vrfb.h>
+#if defined(PVR_OMAPLFB_DRM_FB)
+#include <plat/display.h>
+#include <linux/omap_gpu.h>
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+/* OmapZoom.org OMAP3 2.6.29 kernel tree       - Needs mach/vrfb.h
+ * OmapZoom.org OMAP3 2.6.32 kernel tree       - No additional header required
+ * OmapZoom.org OMAP4 2.6.33 kernel tree       - No additional header required
+ * OmapZoom.org OMAP4 2.6.34 kernel tree       - Needs plat/vrfb.h
+ * Sholes 2.6.32 kernel tree                   - Needs plat/vrfb.h
+ */
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,34))
 #define PVR_OMAPFB3_NEEDS_PLAT_VRFB_H
 #endif
 
 #if defined(PVR_OMAPFB3_NEEDS_PLAT_VRFB_H)
-# include <plat/vrfb.h>
+#include <plat/vrfb.h>
 #else
-# if defined(PVR_OMAPFB3_NEEDS_MACH_VRFB_H)
-#  include <mach/vrfb.h>
-# endif
+#if defined(PVR_OMAPFB3_NEEDS_MACH_VRFB_H)
+#include <mach/vrfb.h>
+#endif
 #endif
 
 #if defined(DEBUG)
 #define        DEBUG PVR_DEBUG
 #undef PVR_DEBUG
 #endif
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
+
+#if defined(CONFIG_DSSCOMP)
+#include <mach/tiler.h>
+#include <video/dsscomp.h>
+#include <plat/dsscomp.h>
+#endif /* defined(CONFIG_DSSCOMP) */
 
 #include "img_defs.h"
 #include "servicesext.h"
 #include "3rdparty_dc_drm_shared.h"
 #endif
 
-#if 0
 #if !defined(PVR_LINUX_USING_WORKQUEUES)
 #error "PVR_LINUX_USING_WORKQUEUES must be defined"
 #endif
-#endif
 
 MODULE_SUPPORTED_DEVICE(DEVNAME);
 
+#if !defined(PVR_OMAPLFB_DRM_FB)
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,34))
 #define OMAP_DSS_DRIVER(drv, dev) struct omap_dss_driver *drv = (dev) != NULL ? (dev)->driver : NULL
 #define OMAP_DSS_MANAGER(man, dev) struct omap_overlay_manager *man = (dev) != NULL ? (dev)->manager : NULL
@@ -105,6 +162,7 @@ MODULE_SUPPORTED_DEVICE(DEVNAME);
 #define OMAP_DSS_MANAGER(man, dev) struct omap_dss_device *man = (dev)
 #define        WAIT_FOR_VSYNC(man)     ((man)->wait_vsync)
 #endif
+#endif /* !defined(PVR_OMAPLFB_DRM_FB) */
 
 void *OMAPLFBAllocKernelMem(unsigned long ulSize)
 {
@@ -186,12 +244,13 @@ OMAPLFB_ERROR OMAPLFBGetLibFuncAddr (char *szFunctionName, PFN_DC_GET_PVRJTABLE
                return (OMAPLFB_ERROR_INVALID_PARAMS);
        }
 
-       
+       /* Nothing to do - should be exported from pvrsrv.ko */
        *ppfnFuncTable = PVRGetDisplayClassJTable;
 
        return (OMAPLFB_OK);
 }
 
+/* Inset a swap buffer into the swap chain work queue */
 void OMAPLFBQueueBufferForSwap(OMAPLFB_SWAPCHAIN *psSwapChain, OMAPLFB_BUFFER *psBuffer)
 {
        int res = queue_work(psSwapChain->psWorkQueue, &psBuffer->sWork);
@@ -202,6 +261,7 @@ void OMAPLFBQueueBufferForSwap(OMAPLFB_SWAPCHAIN *psSwapChain, OMAPLFB_BUFFER *p
        }
 }
 
+/* Process an item on a swap chain work queue */
 static void WorkQueueHandler(struct work_struct *psWork)
 {
        OMAPLFB_BUFFER *psBuffer = container_of(psWork, OMAPLFB_BUFFER, sWork);
@@ -209,16 +269,42 @@ static void WorkQueueHandler(struct work_struct *psWork)
        OMAPLFBSwapHandler(psBuffer);
 }
 
+/* Create a swap chain work queue */
 OMAPLFB_ERROR OMAPLFBCreateSwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
 {
-#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,34))
-        psSwapChain->psWorkQueue = __create_workqueue(DEVNAME, 1, 1, 1);
-#else  
-       psSwapChain->psWorkQueue = create_workqueue(DEVNAME);
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37))
+       /*
+        * Calling alloc_ordered_workqueue with the WQ_FREEZABLE and
+        * WQ_MEM_RECLAIM flags set, (currently) has the same effect as
+        * calling create_freezable_workqueue. None of the other WQ
+        * flags are valid. Setting WQ_MEM_RECLAIM should allow the
+        * workqueue to continue to service the swap chain in low memory
+        * conditions, preventing the driver from holding on to
+        * resources longer than it needs to.
+        */
+#if (LINUX_VERSION_CODE == KERNEL_VERSION(2,6,37))
+       psSwapChain->psWorkQueue = alloc_ordered_workqueue(DEVNAME, WQ_FREEZEABLE | WQ_MEM_RECLAIM);
+#else
+       psSwapChain->psWorkQueue = alloc_ordered_workqueue(DEVNAME, WQ_FREEZABLE | WQ_MEM_RECLAIM);
+#endif
+
+#else
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36))
+       psSwapChain->psWorkQueue = create_freezable_workqueue(DEVNAME);
+#else
+       /*
+        * Create a single-threaded, freezable, rt-prio workqueue.
+        * Such workqueues are frozen with user threads when a system
+        * suspends, before driver suspend entry points are called.
+        * This ensures this driver will not call into the Linux
+        * framebuffer driver after the latter is suspended.
+        */
+       psSwapChain->psWorkQueue = __create_workqueue(DEVNAME, 1, 1, 1);
+#endif
 #endif
        if (psSwapChain->psWorkQueue == NULL)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: create_singlethreaded_workqueue failed\n", __FUNCTION__, psSwapChain->uiFBDevID);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: Couldn't create workqueue\n", __FUNCTION__, psSwapChain->uiFBDevID);
 
                return (OMAPLFB_ERROR_INIT_FAILURE);
        }
@@ -226,26 +312,26 @@ OMAPLFB_ERROR OMAPLFBCreateSwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
        return (OMAPLFB_OK);
 }
 
+/* Prepare buffer for insertion into a swap chain work queue */
 void OMAPLFBInitBufferForSwap(OMAPLFB_BUFFER *psBuffer)
 {
        INIT_WORK(&psBuffer->sWork, WorkQueueHandler);
 }
 
+/* Destroy a swap chain work queue */
 void OMAPLFBDestroySwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
 {
        destroy_workqueue(psSwapChain->psWorkQueue);
 }
 
+/* Flip display to given buffer */
 void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
 {
        struct fb_var_screeninfo sFBVar;
        int res;
        unsigned long ulYResVirtual;
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_lock();
-#else
-       acquire_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_LOCK();
 
        sFBVar = psDevInfo->psLINFBInfo->var;
 
@@ -253,8 +339,63 @@ void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
        sFBVar.yoffset = psBuffer->ulYOffset;
 
        ulYResVirtual = psBuffer->ulYOffset + sFBVar.yres;
-       
+
+#if defined(CONFIG_DSSCOMP)
+       {
+               /*
+                * If using DSSCOMP, we need to use dsscomp queuing for normal
+                * framebuffer updates, so that previously used overlays get
+                * automatically disabled, and manager gets dirtied.  We can
+                * do that because DSSCOMP takes ownership of all pipelines on
+                * a manager.
+                */
+               struct fb_fix_screeninfo sFBFix = psDevInfo->psLINFBInfo->fix;
+               struct dsscomp_setup_dispc_data d =
+               {
+                       .num_ovls = 1,
+                       .num_mgrs = 1,
+                       .mgrs[0].alpha_blending = 1,
+                       .ovls[0] =
+                       {
+                               .cfg =
+                               {
+                                       .win.w = sFBVar.xres,
+                                       .win.h = sFBVar.yres,
+                                       .crop.x = sFBVar.xoffset,
+                                       .crop.y = sFBVar.yoffset,
+                                       .crop.w = sFBVar.xres,
+                                       .crop.h = sFBVar.yres,
+                                       .width = sFBVar.xres_virtual,
+                                       .height = sFBVar.yres_virtual,
+                                       .stride = sFBFix.line_length,
+                                       .enabled = 1,
+                                       .global_alpha = 255,
+                               },
+                       },
+               };
+
+               /* do not map buffer into TILER1D as it is contiguous */
+               struct tiler_pa_info *pas[] = { NULL };
+
+               d.ovls[0].ba = sFBFix.smem_start;
+               omapfb_mode_to_dss_mode(&sFBVar, &d.ovls[0].cfg.color_mode);
+
+               res = dsscomp_gralloc_queue(&d, pas, true, NULL, NULL);
+       }
+#else /* defined(CONFIG_DSSCOMP) */
+       /*
+        * PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY should be defined to work
+        * around flipping problems seen with the Taal LCDs on Blaze.
+        * The work around is safe to use with other types of screen on Blaze
+        * (e.g. HDMI) and on other platforms (e.g. Panda board).
+        */
+#if !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY)
+       /*
+        * Attempt to change the virtual screen resolution if it is too
+        * small.  Note that fb_set_var also pans the display.
+        */
        if (sFBVar.xres_virtual != sFBVar.xres || sFBVar.yres_virtual < ulYResVirtual)
+#endif /* !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY) */
        {
                sFBVar.xres_virtual = sFBVar.xres;
                sFBVar.yres_virtual = ulYResVirtual;
@@ -264,61 +405,298 @@ void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
                res = fb_set_var(psDevInfo->psLINFBInfo, &sFBVar);
                if (res != 0)
                {
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: fb_set_var failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: fb_set_var failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
                }
        }
+#if !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY)
        else
        {
                res = fb_pan_display(psDevInfo->psLINFBInfo, &sFBVar);
                if (res != 0)
                {
-                        printk (" fb_pan api failed \n");
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: fb_pan_display failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: fb_pan_display failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
                }
        }
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_unlock();
-#else
-       release_console_sem();
+#endif /* !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY) */
+#endif /* defined(CONFIG_DSSCOMP) */
+
+       OMAPLFB_CONSOLE_UNLOCK();
+}
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3,1,0)
+#if !defined(PVR_OMAPLFB_DRM_FB) || defined(DEBUG)
+static OMAPLFB_BOOL OMAPLFBValidateDSSUpdateMode(enum omap_dss_update_mode eMode)
+{
+       switch (eMode)
+       {
+               case OMAP_DSS_UPDATE_AUTO:
+               case OMAP_DSS_UPDATE_MANUAL:
+               case OMAP_DSS_UPDATE_DISABLED:
+                       return OMAPLFB_TRUE;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_FALSE;
+}
+
+static OMAPLFB_UPDATE_MODE OMAPLFBFromDSSUpdateMode(enum omap_dss_update_mode eMode)
+{
+       switch (eMode)
+       {
+               case OMAP_DSS_UPDATE_AUTO:
+                       return OMAPLFB_UPDATE_MODE_AUTO;
+               case OMAP_DSS_UPDATE_MANUAL:
+                       return OMAPLFB_UPDATE_MODE_MANUAL;
+               case OMAP_DSS_UPDATE_DISABLED:
+                       return OMAPLFB_UPDATE_MODE_DISABLED;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_UPDATE_MODE_UNDEFINED;
+}
 #endif
+#endif
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3,1,0)
+static OMAPLFB_BOOL OMAPLFBValidateUpdateMode(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return OMAPLFB_TRUE;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_FALSE;
+}
+#endif
+#if 0
+static enum omap_dss_update_mode OMAPLFBToDSSUpdateMode(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+                       return OMAP_DSS_UPDATE_AUTO;
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+                       return OMAP_DSS_UPDATE_MANUAL;
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return OMAP_DSS_UPDATE_DISABLED;
+               default:
+                       break;
+       }
+
+       return -1;
+}
+#endif
+#if defined(DEBUG)
+static const char *OMAPLFBUpdateModeToString(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+                       return "Auto Update Mode";
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+                       return "Manual Update Mode";
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return "Update Mode Disabled";
+               case OMAPLFB_UPDATE_MODE_UNDEFINED:
+                       return "Update Mode Undefined";
+               default:
+                       break;
+       }
+
+       return "Unknown Update Mode";
+}
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3,1,0)
+static const char *OMAPLFBDSSUpdateModeToString(enum omap_dss_update_mode eMode)
+{
+
+       if (!OMAPLFBValidateDSSUpdateMode(eMode))
+       {
+               return "Unknown Update Mode";
+       }
+
+       return OMAPLFBUpdateModeToString(OMAPLFBFromDSSUpdateMode(eMode));
+}
+#endif
+void OMAPLFBPrintInfo(OMAPLFB_DEVINFO *psDevInfo)
+{
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       unsigned uConnectors;
+       unsigned uConnector;
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: DRM framebuffer\n", psDevInfo->uiFBDevID));
+
+       for (psConnector = NULL, uConnectors = 0;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               uConnectors++;
+       }
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: Number of screens (DRM connectors): %u\n", psDevInfo->uiFBDevID, uConnectors));
+
+       if (uConnectors == 0)
+       {
+               return;
+       }
+
+       for (psConnector = NULL, uConnector = 0;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL; uConnector++)
+       {
+               enum omap_dss_update_mode eMode = omap_connector_get_update_mode(psConnector);
+
+               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: Screen %u: %s (%d)\n", psDevInfo->uiFBDevID, uConnector, OMAPLFBDSSUpdateModeToString(eMode), (int)eMode));
+
+       }
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+       OMAPLFB_UPDATE_MODE eMode = OMAPLFBGetUpdateMode(psDevInfo);
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: non-DRM framebuffer\n", psDevInfo->uiFBDevID));
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: %s\n", psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 }
+#endif /* defined(DEBUG) */
 
+/* 
+ * Get display update mode.
+ * If the mode is AUTO, we can wait for VSync, if desired.
+ */
 OMAPLFB_UPDATE_MODE OMAPLFBGetUpdateMode(OMAPLFB_DEVINFO *psDevInfo)
 {
 #if 0
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       OMAPLFB_UPDATE_MODE eMode = OMAPLFB_UPDATE_MODE_UNDEFINED;
+
+       /*
+        * There may be multiple displays connected. If at least one
+        * display is manual update mode, report all screens as being
+        * in that mode.
+        */
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               switch(omap_connector_get_update_mode(psConnector))
+               {
+                       case OMAP_DSS_UPDATE_MANUAL:
+                               eMode = OMAPLFB_UPDATE_MODE_MANUAL;
+                               break;
+                       case OMAP_DSS_UPDATE_DISABLED:
+                               if (eMode == OMAPLFB_UPDATE_MODE_UNDEFINED)
+                               {
+                                       eMode = OMAPLFB_UPDATE_MODE_DISABLED;
+                               }
+                               break;
+                       case OMAP_DSS_UPDATE_AUTO:
+                               /* Fall through to default case */
+                       default:
+                               /* Asssume auto update is possible */
+                               if (eMode != OMAPLFB_UPDATE_MODE_MANUAL)
+                               {
+                                       eMode = OMAPLFB_UPDATE_MODE_AUTO;
+                               }
+                               break;
+               }
+       }
+
+       return eMode;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
 
        enum omap_dss_update_mode eMode;
 
-       if (psDSSDrv == NULL || psDSSDrv->get_update_mode == NULL)
+       if (psDSSDrv == NULL)
        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Can't get update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No DSS device\n", __FUNCTION__, psDevInfo->uiFBDevID));
                return OMAPLFB_UPDATE_MODE_UNDEFINED;
        }
 
-       eMode = psDSSDrv->get_update_mode(psDSSDev);
-       switch(eMode)
+       if (psDSSDrv->get_update_mode == NULL)
        {
-               case OMAP_DSS_UPDATE_AUTO:
+               if (strcmp(psDSSDev->name, "hdmi") == 0)
+               {
+                       return OMAPLFB_UPDATE_MODE_AUTO;
+               }
+//             DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No get_update_mode function\n", __FUNCTION__, psDevInfo->uiFBDevID));
+//             return OMAPLFB_UPDATE_MODE_UNDEFINED;
                        return OMAPLFB_UPDATE_MODE_AUTO;
-               case OMAP_DSS_UPDATE_MANUAL:
-                       return OMAPLFB_UPDATE_MODE_MANUAL;
-               case OMAP_DSS_UPDATE_DISABLED:
-                       return OMAPLFB_UPDATE_MODE_DISABLED;
-               default:
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eMode));
-                       break;
        }
 
-       return OMAPLFB_UPDATE_MODE_UNDEFINED;
+       eMode = psDSSDrv->get_update_mode(psDSSDev);
+       if (!OMAPLFBValidateDSSUpdateMode(eMode))
+       {
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
+       }
+
+       return OMAPLFBFromDSSUpdateMode(eMode);
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 #endif
-        return OMAPLFB_UPDATE_MODE_AUTO;
+return OMAPLFB_UPDATE_MODE_AUTO;
 }
 
+/* Set display update mode */
 OMAPLFB_BOOL OMAPLFBSetUpdateMode(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_UPDATE_MODE eMode)
 {
 #if 0
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       enum omap_dss_update_mode eDSSMode;
+       OMAPLFB_BOOL bSuccess = OMAPLFB_FALSE;
+       OMAPLFB_BOOL bFailure = OMAPLFB_FALSE;
+
+       if (!OMAPLFBValidateUpdateMode(eMode))
+       {
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
+                       return OMAPLFB_FALSE;
+       }
+       eDSSMode = OMAPLFBToDSSUpdateMode(eMode);
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               int iRes = omap_connector_set_update_mode(psConnector, eDSSMode);
+               OMAPLFB_BOOL bRes = (iRes == 0);
+
+
+               bSuccess |= bRes;
+               bFailure |= !bRes;
+       }
+
+       if (!bFailure)
+       {
+               if (!bSuccess)
+               {
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No screens\n", __FUNCTION__, psDevInfo->uiFBDevID));
+               }
+
+               return OMAPLFB_TRUE;
+       }
+
+       if (!bSuccess)
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set %s for any screen\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+               return OMAPLFB_FALSE;
+       }
+
+       if (eMode == OMAPLFB_UPDATE_MODE_AUTO)
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set %s for all screens\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+               return OMAPLFB_FALSE;
+       }
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: %s set for some screens\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
        enum omap_dss_update_mode eDSSMode;
@@ -326,70 +704,60 @@ OMAPLFB_BOOL OMAPLFBSetUpdateMode(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_UPDATE_MOD
 
        if (psDSSDrv == NULL || psDSSDrv->set_update_mode == NULL)
        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Can't set update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Can't set update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
                return OMAPLFB_FALSE;
        }
 
-       switch(eMode)
+       if (!OMAPLFBValidateUpdateMode(eMode))
        {
-               case OMAPLFB_UPDATE_MODE_AUTO:
-                       eDSSMode = OMAP_DSS_UPDATE_AUTO;
-                       break;
-               case OMAPLFB_UPDATE_MODE_MANUAL:
-                       eDSSMode = OMAP_DSS_UPDATE_MANUAL;
-                       break;
-               case OMAPLFB_UPDATE_MODE_DISABLED:
-                       eDSSMode = OMAP_DSS_UPDATE_DISABLED;
-                       break;
-               default:
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eMode));
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
                        return OMAPLFB_FALSE;
        }
+       eDSSMode = OMAPLFBToDSSUpdateMode(eMode);
 
        res = psDSSDrv->set_update_mode(psDSSDev, eDSSMode);
        if (res != 0)
        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: set_update_mode failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: set_update_mode (%s) failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBDSSUpdateModeToString(eDSSMode), res));
        }
 
        return (res == 0);
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 #endif
-        return 1;
+return 1;
 }
 
+/* Wait for VSync */
 OMAPLFB_BOOL OMAPLFBWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
 {
-//struct timeval tv;
-//static time_t curtime,curtime1;
-//     struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
-//     OMAP_DSS_MANAGER(psDSSMan, psDSSDev);
-//        printk("Testing vsync\n");
-/*     if (psDSSMan != NULL && WAIT_FOR_VSYNC(psDSSMan) != NULL)
-       {
-               printk("Vsync call\n");
-               do_gettimeofday(&tv);
-               curtime=tv.tv_usec;
-               printk("The time is %ld\n",curtime);
+#if 0
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               (void) omap_encoder_wait_for_vsync(psConnector->encoder);
+       }
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+       struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
+       OMAP_DSS_MANAGER(psDSSMan, psDSSDev);
+
+       if (psDSSMan != NULL && WAIT_FOR_VSYNC(psDSSMan) != NULL)
+       {
                int res = WAIT_FOR_VSYNC(psDSSMan)(psDSSMan);
-               do_gettimeofday(&tv);
-                curtime1=tv.tv_usec;
-               printk("The time is %ld\n",curtime1);
                if (res != 0)
                {
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Wait for vsync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Wait for vsync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
                        return OMAPLFB_FALSE;
                }
-       }*/
-#if 0
-        struct vps_grpx_ctrl *gctrl;
-        int r;
-        gctrl = vps_grpx_get_ctrl(psDevInfo->uiFBDevID); 
-        printk (" BVSYNC \n");
-        r = gctrl->wait_for_vsync(gctrl);
-        printk (" AVSYNC: %d\n", vsync_num++);
-        return OMAPLFB_TRUE;
+       }
+
+       return OMAPLFB_TRUE;
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 #endif
-//    unsigned long timeout = msecs_to_jiffies(500);
 
 #if FBDEV_PRESENT
       int r;
@@ -397,7 +765,7 @@ OMAPLFB_BOOL OMAPLFBWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
       void grpx_irq_wait_handler(void *data)
       {
           complete((struct completion *)data);
-//     do_gettimeofday(&tv);
+//      do_gettimeofday(&tv);
   //      curtime=tv.tv_usec;
 //printk("The time in handler is %ld\n",curtime);
       }
@@ -420,11 +788,31 @@ OMAPLFB_BOOL OMAPLFBWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
       }
 #endif
       return OMAPLFB_TRUE;
+
 }
 
+/*
+ * Wait for screen to update.  If the screen is in manual or auto update
+ * mode, we can call this function to wait for the screen to update.
+ */
 OMAPLFB_BOOL OMAPLFBManualSync(OMAPLFB_DEVINFO *psDevInfo)
 {
 #if 0
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL; )
+       {
+               /* Try manual sync first, then try wait for vsync */
+               if (omap_connector_sync(psConnector) != 0)
+               {
+                       (void) omap_encoder_wait_for_vsync(psConnector->encoder);
+               }
+       }
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
 
@@ -433,15 +821,21 @@ OMAPLFB_BOOL OMAPLFBManualSync(OMAPLFB_DEVINFO *psDevInfo)
                int res = psDSSDrv->sync(psDSSDev);
                if (res != 0)
                {
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: Sync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: Sync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                        return OMAPLFB_FALSE;
                }
        }
-#endif
 
        return OMAPLFB_TRUE;
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
+#endif
+return OMAPLFB_TRUE;
 }
 
+/*
+ * If the screen is manual or auto update mode, wait for the screen to
+ * update.
+ */
 OMAPLFB_BOOL OMAPLFBCheckModeAndSync(OMAPLFB_DEVINFO *psDevInfo)
 {
        OMAPLFB_UPDATE_MODE eMode = OMAPLFBGetUpdateMode(psDevInfo);
@@ -458,6 +852,7 @@ OMAPLFB_BOOL OMAPLFBCheckModeAndSync(OMAPLFB_DEVINFO *psDevInfo)
        return OMAPLFB_TRUE;
 }
 
+/* Linux Framebuffer event notification handler */
 static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
                              unsigned long event, void *data)
 {
@@ -466,7 +861,7 @@ static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
        struct fb_info *psFBInfo = psFBEvent->info;
        OMAPLFB_BOOL bBlanked;
 
-       
+       /* Only interested in blanking events */
        if (event != FB_EVENT_BLANK)
        {
                return 0;
@@ -503,47 +898,33 @@ static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
        return 0;
 }
 
+/* Unblank the screen */
 OMAPLFB_ERROR OMAPLFBUnblankDisplay(OMAPLFB_DEVINFO *psDevInfo)
 {
-       int res;
 #ifdef FBDEV_PRESENT
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_lock();
-#else
-       acquire_console_sem();
-#endif
+       int res;
+
+       OMAPLFB_CONSOLE_LOCK();
        res = fb_blank(psDevInfo->psLINFBInfo, 0);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_unlock();
-#else
-       release_console_sem();
-#endif
+       OMAPLFB_CONSOLE_UNLOCK();
        if (res != 0 && res != -EINVAL)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_blank failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                return (OMAPLFB_ERROR_GENERIC);
        }
 #endif
-
        return (OMAPLFB_OK);
 }
 
 #ifdef CONFIG_HAS_EARLYSUSPEND
 
+/* Blank the screen */
 static void OMAPLFBBlankDisplay(OMAPLFB_DEVINFO *psDevInfo)
 {
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_lock();
-#else
-       acquire_console_sem();
-#endif
+       OMAPLFB_CONSOLE_LOCK();
        fb_blank(psDevInfo->psLINFBInfo, 1);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-       console_unlock();
-#else
-       release_console_sem();
-#endif
+       OMAPLFB_CONSOLE_UNLOCK();
 }
 
 static void OMAPLFBEarlySuspendHandler(struct early_suspend *h)
@@ -580,14 +961,15 @@ static void OMAPLFBEarlyResumeHandler(struct early_suspend *h)
        }
 }
 
-#endif 
+#endif /* CONFIG_HAS_EARLYSUSPEND */
 
+/* Set up Linux Framebuffer event notification */
 OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 {
        int                res;
        OMAPLFB_ERROR         eError;
 
-       
+       /* Set up Linux Framebuffer event notification */
        memset(&psDevInfo->sLINNotifBlock, 0, sizeof(psDevInfo->sLINNotifBlock));
 
        psDevInfo->sLINNotifBlock.notifier_call = OMAPLFBFrameBufferEvents;
@@ -598,7 +980,7 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        res = fb_register_client(&psDevInfo->sLINNotifBlock);
        if (res != 0)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_register_client failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
 
                return (OMAPLFB_ERROR_GENERIC);
@@ -607,7 +989,7 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        eError = OMAPLFBUnblankDisplay(psDevInfo);
        if (eError != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: UnblankDisplay failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eError);
                return eError;
        }
@@ -615,13 +997,14 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 #ifdef CONFIG_HAS_EARLYSUSPEND
        psDevInfo->sEarlySuspend.suspend = OMAPLFBEarlySuspendHandler;
        psDevInfo->sEarlySuspend.resume = OMAPLFBEarlyResumeHandler;
-       psDevInfo->sEarlySuspend.level = EARLY_SUSPEND_LEVEL_BLANK_SCREEN;
+       psDevInfo->sEarlySuspend.level = EARLY_SUSPEND_LEVEL_DISABLE_FB + 1;
        register_early_suspend(&psDevInfo->sEarlySuspend);
 #endif
 
        return (OMAPLFB_OK);
 }
 
+/* Disable Linux Framebuffer event notification */
 OMAPLFB_ERROR OMAPLFBDisableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 {
        int res;
@@ -630,11 +1013,11 @@ OMAPLFB_ERROR OMAPLFBDisableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        unregister_early_suspend(&psDevInfo->sEarlySuspend);
 #endif
 
-       
+       /* Unregister for Framebuffer events */
        res = fb_unregister_client(&psDevInfo->sLINNotifBlock);
        if (res != 0)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_unregister_client failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                return (OMAPLFB_ERROR_GENERIC);
        }
@@ -660,13 +1043,13 @@ static OMAPLFB_DEVINFO *OMAPLFBPVRDevIDToDevInfo(unsigned uiPVRDevID)
                }
        }
 
-       printk(KERN_WARNING DRIVER_PREFIX
+       printk(KERN_ERR DRIVER_PREFIX
                ": %s: PVR Device %u: Couldn't find device\n", __FUNCTION__, uiPVRDevID);
 
        return NULL;
 }
 
-int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg, struct drm_file unref__ *pFile)
+int PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Ioctl)(struct drm_device unref__ *dev, void *arg, struct drm_file unref__ *pFile)
 {
        uint32_t *puiArgs;
        uint32_t uiCmd;
@@ -745,7 +1128,7 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
                                                pszMode = "(Unknown Mode)";
                                                break;
                                }
-                               printk (KERN_WARNING DRIVER_PREFIX ": %s: PVR Device %u: Display %s\n",
+                               printk(KERN_WARNING DRIVER_PREFIX ": %s: PVR Device %u: Display %s\n",
                                __FUNCTION__, uiPVRDevID, pszMode);
                        }
 #endif
@@ -773,18 +1156,10 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
                        {
                                flush_workqueue(psDevInfo->psSwapChain->psWorkQueue);
                        }
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-                       console_lock();
-#else
-                       acquire_console_sem();
-#endif
-                       ret = fb_blank(psDevInfo->psLINFBInfo, iFBMode);
 
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-                       console_unlock();
-#else
-                       release_console_sem();
-#endif
+                       OMAPLFB_CONSOLE_LOCK();
+                       ret = fb_blank(psDevInfo->psLINFBInfo, iFBMode);
+                       OMAPLFB_CONSOLE_UNLOCK();
 
                        OMAPLFBCreateSwapChainUnLock(psDevInfo);
 
@@ -801,8 +1176,9 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
 }
 #endif
 
+/* Insert the driver into the kernel */
 #if defined(SUPPORT_DRI_DRM)
-int PVR_DRM_MAKENAME(omaplfb, _Init)(struct drm_device unref__ *dev)
+int PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Init)(struct drm_device unref__ *dev)
 #else
 static int __init OMAPLFB_Init(void)
 #endif
@@ -810,7 +1186,7 @@ static int __init OMAPLFB_Init(void)
 
        if(OMAPLFBInit() != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: OMAPLFBInit failed\n", __FUNCTION__);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: OMAPLFBInit failed\n", __FUNCTION__);
                return -ENODEV;
        }
 
@@ -818,19 +1194,26 @@ static int __init OMAPLFB_Init(void)
 
 }
 
+/* Remove the driver from the kernel */
 #if defined(SUPPORT_DRI_DRM)
-void PVR_DRM_MAKENAME(omaplfb, _Cleanup)(struct drm_device unref__ *dev)
+void PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Cleanup)(struct drm_device unref__ *dev)
 #else
 static void __exit OMAPLFB_Cleanup(void)
 #endif
 {    
        if(OMAPLFBDeInit() != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: OMAPLFBDeInit failed\n", __FUNCTION__);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: OMAPLFBDeInit failed\n", __FUNCTION__);
        }
 }
 
 #if !defined(SUPPORT_DRI_DRM)
+/*
+ These macro calls define the initialisation and removal functions of the
+ driver.  Although they are prefixed `module_', they apply when compiling
+ statically as well; in both cases they define the function the kernel will
+ run to start/stop the driver.
+*/
 late_initcall(OMAPLFB_Init);
 module_exit(OMAPLFB_Cleanup);
 #endif
index 9b6d240..addbfc2 100644 (file)
@@ -1,29 +1,46 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OMAP Linux display driver shared DRM structures
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    OMAP Linux display driver DRM structures shared between
+                kernel and user space.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
 #ifndef __3RDPARTY_DC_DRM_SHARED_H__
 #define __3RDPARTY_DC_DRM_SHARED_H__
 #if defined(SUPPORT_DRI_DRM)
@@ -40,6 +57,9 @@
 #define        PVR_DRM_DISP_ARG_DEV            1
 #define        PVR_DRM_DISP_NUM_ARGS           2
 
-#endif 
-#endif 
+#endif /* defined(SUPPORT_DRI_DRM) */
+#endif /* __3RDPARTY_DC_DRM_SHARED_H__ */
 
+/******************************************************************************
+ End of file (3rdparty_dc_drm_shared.h)
+******************************************************************************/
index 8ac212e..1ae2359 100644 (file)
@@ -14,6 +14,7 @@ EXTRA_CFLAGS =        -DLINUX \
                -I$(PVR_BUILD_DIR)/include4 \
                -I$(PVR_BUILD_DIR)/services4/include \
                -I$(PVR_BUILD_DIR)/services4/system/$(PVR_SYSTEM) \
+               -I$(KERNELDIR)/drivers/video/omap2 \
                -I$(PVR_BUILD_DIR)/services4/system/include \
                $(SYS_CFLAGS.1) \
 
diff --git a/services4/3rdparty/dc_ti81xx_linux/Kbuild.mk b/services4/3rdparty/dc_ti81xx_linux/Kbuild.mk
new file mode 100644 (file)
index 0000000..eca9351
--- /dev/null
@@ -0,0 +1,49 @@
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
+# 
+# The contents of this file are subject to the MIT license as set out below.
+# 
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+# 
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+# 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
+# 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#   
+### ###########################################################################
+
+ccflags-y += \
+       -I$(TOP)/services4/3rdparty/dc_omapfb3_linux \
+       -I$(KERNELDIR)/drivers/video/omap2 \
+       -I$(KERNELDIR)/arch/arm/plat-omap/include
+
+omaplfb-y += \
+       services4/3rdparty/dc_omapfb3_linux/omaplfb_displayclass.o \
+       services4/3rdparty/dc_omapfb3_linux/omaplfb_linux.o
diff --git a/services4/3rdparty/dc_ti81xx_linux/Linux.mk b/services4/3rdparty/dc_ti81xx_linux/Linux.mk
new file mode 100644 (file)
index 0000000..7574073
--- /dev/null
@@ -0,0 +1,46 @@
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
+# 
+# The contents of this file are subject to the MIT license as set out below.
+# 
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+# 
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+# 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
+# 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#   
+### ###########################################################################
+
+modules := dc_omapfb3_linux
+
+dc_omapfb3_linux_type := kernel_module
+dc_omapfb3_linux_target := omaplfb.ko
+dc_omapfb3_linux_makefile := $(THIS_DIR)/Kbuild.mk
diff --git a/services4/3rdparty/dc_ti81xx_linux/kbuild/Makefile b/services4/3rdparty/dc_ti81xx_linux/kbuild/Makefile
deleted file mode 100644 (file)
index f52617a..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-#
-# Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
-# 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
-# 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
-# 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
-# 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
-# 
-#
-
-MODULE         = $(DISPLAY_CONTROLLER)
-
-INCLUDES =
-
-SOURCES        =
-
-SYM_VERS_DEPS = $(EURASIAROOT)/services4/srvkm/env/linux
-
-include $(EURASIAROOT)/services4/$(DISPLAY_CONTROLLER_DIR)/makefile.linux.common
-
-include $(EURASIAROOT)/eurasiacon/build/linux/kbuild/Makefile.kbuild_subdir_common
diff --git a/services4/3rdparty/dc_ti81xx_linux/makefile.linux.common b/services4/3rdparty/dc_ti81xx_linux/makefile.linux.common
deleted file mode 100644 (file)
index d5b4a30..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-#
-# Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
-# 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
-# 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
-# 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
-# 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
-# 
-#
-#
-
-ifeq ($(SUPPORT_DRI_DRM),1)
-DISPLAY_CONTROLLER_SOURCES_ROOT = $(KBUILDROOT)/$(DISPLAY_CONTROLLER_DIR)
-MODULE_CFLAGS += -DPVR_DISPLAY_CONTROLLER_DRM_IOCTL
-else
-DISPLAY_CONTROLLER_SOURCES_ROOT = ..
-endif
-
-INCLUDES +=    -I$(EURASIAROOT)/include4 \
-               -I$(EURASIAROOT)/services4/include \
-               -I$(EURASIAROOT)/services4/system/$(PVR_SYSTEM) \
-               -I$(EURASIAROOT)/services4/system/include \
-               -I$(KERNELDIR)/drivers/video/omap2 \
-               -I$(KERNELDIR)/arch/arm/plat-omap/include
-
-SOURCES        +=      $(DISPLAY_CONTROLLER_SOURCES_ROOT)/omaplfb_displayclass.c \
-                       $(DISPLAY_CONTROLLER_SOURCES_ROOT)/omaplfb_linux.c
index 881a49d..c69640d 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          OMAP Linux display driver structures and prototypes
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
 #ifndef __OMAPLFB_H__
 #define __OMAPLFB_H__
 
 #include <linux/earlysuspend.h>
 #endif
 
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38))
+#define        OMAPLFB_CONSOLE_LOCK()          console_lock()
+#define        OMAPLFB_CONSOLE_UNLOCK()        console_unlock()
+#else
+#define        OMAPLFB_CONSOLE_LOCK()          acquire_console_sem()
+#define        OMAPLFB_CONSOLE_UNLOCK()        release_console_sem()
+#endif
+
 #define unref__ __attribute__ ((unused))
 
 typedef void *       OMAPLFB_HANDLE;
@@ -55,6 +78,7 @@ typedef       atomic_t        OMAPLFB_ATOMIC_BOOL;
 
 typedef atomic_t       OMAPLFB_ATOMIC_INT;
 
+/* OMAPLFB buffer structure */
 typedef struct OMAPLFB_BUFFER_TAG
 {
        struct OMAPLFB_BUFFER_TAG       *psNext;
@@ -62,11 +86,11 @@ typedef struct OMAPLFB_BUFFER_TAG
 
        struct work_struct sWork;
 
-       
+       /* Position of this buffer in the virtual framebuffer */
        unsigned long                   ulYOffset;
 
-       
-       
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
        IMG_SYS_PHYADDR                 sSysAddr;
        IMG_CPU_VIRTADDR                sCPUVAddr;
        PVRSRV_SYNC_DATA                *psSyncData;
@@ -75,27 +99,34 @@ typedef struct OMAPLFB_BUFFER_TAG
        unsigned long                   ulSwapInterval;
 } OMAPLFB_BUFFER;
 
+/* OMAPLFB swapchain structure */
 typedef struct OMAPLFB_SWAPCHAIN_TAG
 {
-       
+       /* Swap chain ID */
        unsigned int                    uiSwapChainID;
 
-       
+       /* number of buffers in swapchain */
        unsigned long                   ulBufferCount;
 
-       
+       /* list of buffers in the swapchain */
        OMAPLFB_BUFFER                  *psBuffer;
 
-       
+       /* Swap chain work queue */
        struct workqueue_struct         *psWorkQueue;
 
-       
+       /*
+        * Set if we didn't manage to wait for VSync on last swap,
+        * or if we think we need to wait for VSync on the next flip.
+        * The flag helps to avoid jitter when the screen is
+        * unblanked, by forcing an extended wait for VSync before
+        * attempting the next flip.
+        */
        OMAPLFB_BOOL                    bNotVSynced;
 
-       
+       /* Previous number of blank events */
        int                             iBlankEvents;
 
-       
+       /* Framebuffer Device ID for messages (e.g. printk) */
        unsigned int                    uiFBDevID;
 } OMAPLFB_SWAPCHAIN;
 
@@ -110,75 +141,83 @@ typedef struct OMAPLFB_FBINFO_TAG
        unsigned long       ulPhysicalWidthmm;
        unsigned long       ulPhysicalHeightmm;
 
-       
-       
-       IMG_SYS_PHYADDR     sSysAddr;
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
+       IMG_SYS_PHYADDR     sSysAddr;//system physical address
        IMG_CPU_VIRTADDR    sCPUVAddr;
 
-       
+       /* pixelformat of system/primary surface */
        PVRSRV_PIXEL_FORMAT ePixelFormat;
-}OMAPLFB_FBINFO;
 
+#if defined(CONFIG_DSSCOMP)
+       OMAPLFB_BOOL            bIs2D;
+       IMG_SYS_PHYADDR         *psPageList;
+       struct ion_handle       *psIONHandle;
+       IMG_UINT32                      uiBytesPerPixel;
+#endif
+} OMAPLFB_FBINFO;
+
+/* kernel device information structure */
 typedef struct OMAPLFB_DEVINFO_TAG
 {
-       
+       /* Framebuffer Device ID */
        unsigned int            uiFBDevID;
 
-       
+       /* PVR Device ID */
        unsigned int            uiPVRDevID;
 
-       
+       /* Swapchain create/destroy mutex */
        struct mutex            sCreateSwapChainMutex;
 
-       
+       /* system surface info */
        OMAPLFB_BUFFER          sSystemBuffer;
 
-       
+       /* jump table into PVR services */
        PVRSRV_DC_DISP2SRV_KMJTABLE     sPVRJTable;
        
-       
+       /* jump table into DC */
        PVRSRV_DC_SRV2DISP_KMJTABLE     sDCJTable;
 
-       
+       /* fb info structure */
        OMAPLFB_FBINFO          sFBInfo;
 
-       
+       /* Only one swapchain supported by this device so hang it here */
        OMAPLFB_SWAPCHAIN      *psSwapChain;
 
-       
+       /* Swap chain ID */
        unsigned int            uiSwapChainID;
 
-       
+       /* True if PVR Services is flushing its command queues */
        OMAPLFB_ATOMIC_BOOL     sFlushCommands;
 
-       
+       /* pointer to linux frame buffer information structure */
        struct fb_info         *psLINFBInfo;
 
-       
+       /* Linux Framebuffer event notification block */
        struct notifier_block   sLINNotifBlock;
 
-       
-       
+       /* IMG structures used, to minimise API function code */
+       /* replace with own structures where necessary */
 
-       
+       /* Address of the surface being displayed */
        IMG_DEV_VIRTADDR        sDisplayDevVAddr;
 
        DISPLAY_INFO            sDisplayInfo;
 
-       
+       /* Display format */
        DISPLAY_FORMAT          sDisplayFormat;
        
-       
+       /* Display dimensions */
        DISPLAY_DIMS            sDisplayDim;
 
-       
+       /* True if screen is blanked */
        OMAPLFB_ATOMIC_BOOL     sBlanked;
 
-       
+       /* Number of blank/unblank events */
        OMAPLFB_ATOMIC_INT      sBlankEvents;
 
 #ifdef CONFIG_HAS_EARLYSUSPEND
-       
+       /* Set by early suspend */
        OMAPLFB_ATOMIC_BOOL     sEarlySuspendFlag;
 
        struct early_suspend    sEarlySuspend;
@@ -192,6 +231,7 @@ typedef struct OMAPLFB_DEVINFO_TAG
 
 #define        OMAPLFB_PAGE_SIZE 4096
 
+/* DEBUG only printk */
 #ifdef DEBUG
 #define        DEBUG_PRINTK(x) printk x
 #else
@@ -203,6 +243,10 @@ typedef struct OMAPLFB_DEVINFO_TAG
 #define        DEVNAME DRVNAME
 #define        DRIVER_PREFIX DRVNAME
 
+/*!
+ *****************************************************************************
+ * Error values
+ *****************************************************************************/
 typedef enum _OMAPLFB_ERROR_
 {
        OMAPLFB_OK                             =  0,
@@ -232,6 +276,7 @@ typedef enum _OMAPLFB_UPDATE_MODE_
 OMAPLFB_ERROR OMAPLFBInit(void);
 OMAPLFB_ERROR OMAPLFBDeInit(void);
 
+/* OS Specific APIs */
 OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID);
 unsigned OMAPLFBMaxFBDevIDPlusOne(void);
 void *OMAPLFBAllocKernelMem(unsigned long ulSize);
@@ -265,5 +310,15 @@ void OMAPLFBAtomicIntSet(OMAPLFB_ATOMIC_INT *psAtomic, int iVal);
 int OMAPLFBAtomicIntRead(OMAPLFB_ATOMIC_INT *psAtomic);
 void OMAPLFBAtomicIntInc(OMAPLFB_ATOMIC_INT *psAtomic);
 
-#endif 
+#if defined(DEBUG)
+void OMAPLFBPrintInfo(OMAPLFB_DEVINFO *psDevInfo);
+#else
+#define        OMAPLFBPrintInfo(psDevInfo)
+#endif
+
+#endif /* __OMAPLFB_H__ */
+
+/******************************************************************************
+ End of file (omaplfb.h)
+******************************************************************************/
 
index b1bb8df..ec0b7c4 100644 (file)
@@ -1,28 +1,77 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OMAP common display driver components
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with 3rd Party display hardware.  It is NOT a specification for
+ a display controller driver, rather a specification to extend the API for a
+ pre-existing driver for the display hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying display hardware, allowing
+ the client drivers to indirectly control the display hardware and access its
+ associated memory.
+ Functions of the API include
+ - query primary surface attributes (width, height, stride, pixel format, CPU
+     physical and virtual address)
+ - swap/flip chain creation and subsequent query of surface attributes
+ - asynchronous display surface flipping, taking account of asynchronous read
+ (flip) and write (render) operations to the display surface
+
+ Note: having queried surface attributes the client drivers are able to map the
+ display memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the display surface handle.
+
+ This code is intended to be an example of how a pre-existing display driver may
+ be extended to support the 3rd Party Display interface to POWERVR Services
+ - IMG is not providing a display driver implementation.
+ **************************************************************************/
+
+/*
+ * OMAP Linux 3rd party display driver.
+ * This is based on the Generic PVR Linux Framebuffer 3rd party display
+ * driver, with OMAP specific extensions to support flipping.
+ */
 
 #include <linux/version.h>
 #include <linux/kernel.h>
 #include <linux/string.h>
 #include <linux/notifier.h>
 
+/* IMG services headers */
 #include "img_defs.h"
 #include "servicesext.h"
 #include "kerneldisplay.h"
 #include "omaplfb.h"
 
+#if defined(CONFIG_DSSCOMP)
+
+#if !defined(CONFIG_ION_OMAP)
+#error CONFIG_DSSCOMP support requires CONFIG_ION_OMAP
+#endif
+
+#include <linux/ion.h>
+#include <linux/omap_ion.h>
+
+extern struct ion_client *gpsIONClient;
+
+#include <mach/tiler.h>
+#include <video/dsscomp.h>
+#include <plat/dsscomp.h>
+
+#endif /* defined(CONFIG_DSSCOMP) */
+
 #define OMAPLFB_COMMAND_COUNT          1
 
 #define        OMAPLFB_VSYNC_SETTLE_COUNT      5
 
-#define        OMAPLFB_MAX_NUM_DEVICES         1 // FB_MAX
+//#define      OMAPLFB_MAX_NUM_DEVICES         FB_MAX
+#define        OMAPLFB_MAX_NUM_DEVICES         1
 #if (OMAPLFB_MAX_NUM_DEVICES > FB_MAX)
 #error "OMAPLFB_MAX_NUM_DEVICES must not be greater than FB_MAX"
 #endif
 
 static OMAPLFB_DEVINFO *gapsDevInfo[OMAPLFB_MAX_NUM_DEVICES];
 
+/* Top level 'hook ptr' */
 static PFN_DC_GET_PVRJTABLE gpfnGetPVRJTable = NULL;
 
+/* Round x up to a multiple of y */
 static inline unsigned long RoundUpToMultiple(unsigned long x, unsigned long y)
 {
        unsigned long div = x / y;
@@ -58,6 +128,7 @@ static inline unsigned long RoundUpToMultiple(unsigned long x, unsigned long y)
        return (div + ((rem == 0) ? 0 : 1)) * y;
 }
 
+/* Greatest common divisor of x and y */
 static unsigned long GCD(unsigned long x, unsigned long y)
 {
        while (y != 0)
@@ -70,6 +141,7 @@ static unsigned long GCD(unsigned long x, unsigned long y)
        return x;
 }
 
+/* Least common multiple of x and y */
 static unsigned long LCM(unsigned long x, unsigned long y)
 {
        unsigned long gcd = GCD(x, y);
@@ -82,6 +154,7 @@ unsigned OMAPLFBMaxFBDevIDPlusOne(void)
        return OMAPLFB_MAX_NUM_DEVICES;
 }
 
+/* Returns DevInfo pointer for a given device */
 OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID)
 {
        WARN_ON(uiFBDevID >= OMAPLFBMaxFBDevIDPlusOne());
@@ -94,6 +167,7 @@ OMAPLFB_DEVINFO *OMAPLFBGetDevInfoPtr(unsigned uiFBDevID)
        return gapsDevInfo[uiFBDevID];
 }
 
+/* Sets the DevInfo pointer for a given device */
 static inline void OMAPLFBSetDevInfoPtr(unsigned uiFBDevID, OMAPLFB_DEVINFO *psDevInfo)
 {
        WARN_ON(uiFBDevID >= OMAPLFB_MAX_NUM_DEVICES);
@@ -110,6 +184,7 @@ static inline OMAPLFB_BOOL SwapChainHasChanged(OMAPLFB_DEVINFO *psDevInfo, OMAPL
                (psDevInfo->uiSwapChainID != psSwapChain->uiSwapChainID);
 }
 
+/* Don't wait for vertical sync */
 static inline OMAPLFB_BOOL DontWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
 {
        OMAPLFB_BOOL bDontWait;
@@ -126,6 +201,10 @@ static inline OMAPLFB_BOOL DontWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
        return bDontWait;
 }
 
+/*
+ * SetDCState
+ * Called from services.
+ */
 static IMG_VOID SetDCState(IMG_HANDLE hDevice, IMG_UINT32 ui32State)
 {
        OMAPLFB_DEVINFO *psDevInfo = (OMAPLFB_DEVINFO *)hDevice;
@@ -138,11 +217,18 @@ static IMG_VOID SetDCState(IMG_HANDLE hDevice, IMG_UINT32 ui32State)
                case DC_STATE_NO_FLUSH_COMMANDS:
                        OMAPLFBAtomicBoolSet(&psDevInfo->sFlushCommands, OMAPLFB_FALSE);
                        break;
+               case DC_STATE_FORCE_SWAP_TO_SYSTEM:
+                       OMAPLFBFlip(psDevInfo, &psDevInfo->sSystemBuffer);
+                       break;
                default:
                        break;
        }
 }
 
+/*
+ * OpenDCDevice
+ * Called from services.
+ */
 static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                                  IMG_HANDLE *phDevice,
                                  PVRSRV_SYNC_DATA* psSystemBufferSyncData)
@@ -167,7 +253,7 @@ static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                return PVRSRV_ERROR_INVALID_DEVICE;
        }
 
-       
+       /* store the system surface sync data */
        psDevInfo->sSystemBuffer.psSyncData = psSystemBufferSyncData;
        
        eError = OMAPLFBUnblankDisplay(psDevInfo);
@@ -178,12 +264,16 @@ static PVRSRV_ERROR OpenDCDevice(IMG_UINT32 uiPVRDevID,
                return PVRSRV_ERROR_UNBLANK_DISPLAY_FAILED;
        }
 
-       
+       /* return handle to the devinfo */
        *phDevice = (IMG_HANDLE)psDevInfo;
        
        return PVRSRV_OK;
 }
 
+/*
+ * CloseDCDevice
+ * Called from services.
+ */
 static PVRSRV_ERROR CloseDCDevice(IMG_HANDLE hDevice)
 {
 #if defined(SUPPORT_DRI_DRM)
@@ -197,6 +287,10 @@ static PVRSRV_ERROR CloseDCDevice(IMG_HANDLE hDevice)
        return PVRSRV_OK;
 }
 
+/*
+ * EnumDCFormats
+ * Called from services.
+ */
 static PVRSRV_ERROR EnumDCFormats(IMG_HANDLE hDevice,
                                   IMG_UINT32 *pui32NumFormats,
                                   DISPLAY_FORMAT *psFormat)
@@ -220,6 +314,10 @@ static PVRSRV_ERROR EnumDCFormats(IMG_HANDLE hDevice,
        return PVRSRV_OK;
 }
 
+/*
+ * EnumDCDims
+ * Called from services.
+ */
 static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice, 
                                DISPLAY_FORMAT *psFormat,
                                IMG_UINT32 *pui32NumDims,
@@ -236,7 +334,7 @@ static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice,
 
        *pui32NumDims = 1;
 
-       
+       /* No need to look at psFormat; there is only one */
        if(psDim)
        {
                psDim[0] = psDevInfo->sDisplayDim;
@@ -246,6 +344,10 @@ static PVRSRV_ERROR EnumDCDims(IMG_HANDLE hDevice,
 }
 
 
+/*
+ * GetDCSystemBuffer
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCSystemBuffer(IMG_HANDLE hDevice, IMG_HANDLE *phBuffer)
 {
        OMAPLFB_DEVINFO *psDevInfo;
@@ -263,6 +365,10 @@ static PVRSRV_ERROR GetDCSystemBuffer(IMG_HANDLE hDevice, IMG_HANDLE *phBuffer)
 }
 
 
+/*
+ * GetDCInfo
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCInfo(IMG_HANDLE hDevice, DISPLAY_INFO *psDCInfo)
 {
        OMAPLFB_DEVINFO *psDevInfo;
@@ -279,6 +385,10 @@ static PVRSRV_ERROR GetDCInfo(IMG_HANDLE hDevice, DISPLAY_INFO *psDCInfo)
        return PVRSRV_OK;
 }
 
+/*
+ * GetDCBufferAddr
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
                                     IMG_HANDLE        hBuffer, 
                                     IMG_SYS_PHYADDR   **ppsSysAddr,
@@ -323,7 +433,11 @@ static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
 
        if (ppvCpuVAddr)
        {
+#if defined(CONFIG_DSSCOMP)
+               *ppvCpuVAddr = psDevInfo->sFBInfo.bIs2D ? NULL : psSystemBuffer->sCPUVAddr;
+#else
                *ppvCpuVAddr = psSystemBuffer->sCPUVAddr;
+#endif
        }
 
        if (phOSMapInfo)
@@ -333,12 +447,28 @@ static PVRSRV_ERROR GetDCBufferAddr(IMG_HANDLE        hDevice,
 
        if (pbIsContiguous)
        {
+#if defined(CONFIG_DSSCOMP)
+               *pbIsContiguous = !psDevInfo->sFBInfo.bIs2D;
+#else
                *pbIsContiguous = IMG_TRUE;
+#endif
        }
 
+#if defined(CONFIG_DSSCOMP)
+       if (psDevInfo->sFBInfo.bIs2D)
+       {
+               int i = (psSystemBuffer->sSysAddr.uiAddr - psDevInfo->sFBInfo.psPageList->uiAddr) >> PAGE_SHIFT;
+               *ppsSysAddr = psDevInfo->sFBInfo.psPageList + psDevInfo->sFBInfo.ulHeight * i;
+       }
+#endif
+
        return PVRSRV_OK;
 }
 
+/*
+ * CreateDCSwapChain
+ * Called from services.
+ */
 static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                                       IMG_UINT32 ui32Flags,
                                       DISPLAY_SURF_ATTRIBUTES *psDstSurfAttrib,
@@ -358,7 +488,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        UNREFERENCED_PARAMETER(ui32OEMFlags);
        
-       
+       /* Check parameters */
        if(!hDevice
        || !psDstSurfAttrib
        || !psSrcSurfAttrib
@@ -370,7 +500,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        psDevInfo = (OMAPLFB_DEVINFO*)hDevice;
        
-       
+       /* Do we support swap chains? */
        if (psDevInfo->sDisplayInfo.ui32MaxSwapChains == 0)
        {
                return PVRSRV_ERROR_NOT_SUPPORTED;
@@ -378,14 +508,14 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
 
        OMAPLFBCreateSwapChainLock(psDevInfo);
 
-       
+       /* The driver only supports a single swapchain */
        if(psDevInfo->psSwapChain != NULL)
        {
                eError = PVRSRV_ERROR_FLIP_CHAIN_EXISTS;
                goto ExitUnLock;
        }
        
-       
+       /* Check the buffer count */
        if(ui32BufferCount > psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers)
        {
                eError = PVRSRV_ERROR_TOOMANYBUFFERS;
@@ -398,16 +528,23 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                goto ExitUnLock;
        }
 
-       
+       /*
+        * We will allocate the swap chain buffers at the back of the frame
+        * buffer area.  This preserves the front portion, which may be being
+        * used by other Linux Framebuffer based applications.
+        */
        ui32BuffersToSkip = psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers - ui32BufferCount;
 
-       
+       /* 
+        *      Verify the DST/SRC attributes,
+        *      SRC/DST must match the current display mode config
+       */
        if(psDstSurfAttrib->pixelformat != psDevInfo->sDisplayFormat.pixelformat
        || psDstSurfAttrib->sDims.ui32ByteStride != psDevInfo->sDisplayDim.ui32ByteStride
        || psDstSurfAttrib->sDims.ui32Width != psDevInfo->sDisplayDim.ui32Width
        || psDstSurfAttrib->sDims.ui32Height != psDevInfo->sDisplayDim.ui32Height)
        {
-               
+               /* DST doesn't match the current mode */
                eError = PVRSRV_ERROR_INVALID_PARAMS;
                goto ExitUnLock;
        }               
@@ -417,12 +554,12 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
        || psDstSurfAttrib->sDims.ui32Width != psSrcSurfAttrib->sDims.ui32Width
        || psDstSurfAttrib->sDims.ui32Height != psSrcSurfAttrib->sDims.ui32Height)
        {
-               
+               /* DST doesn't match the SRC */
                eError = PVRSRV_ERROR_INVALID_PARAMS;
                goto ExitUnLock;
        }               
 
-       
+       /* check flags if implementation requires them */
        UNREFERENCED_PARAMETER(ui32Flags);
        
 #if defined(PVR_OMAPFB3_UPDATE_MODE)
@@ -431,7 +568,7 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set frame buffer update mode %d\n", __FUNCTION__, psDevInfo->uiFBDevID, PVR_OMAPFB3_UPDATE_MODE);
        }
 #endif
-       
+       /* create a swapchain structure */
        psSwapChain = (OMAPLFB_SWAPCHAIN*)OMAPLFBAllocKernelMem(sizeof(OMAPLFB_SWAPCHAIN));
        if(!psSwapChain)
        {
@@ -451,20 +588,27 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
        psSwapChain->bNotVSynced = OMAPLFB_TRUE;
        psSwapChain->uiFBDevID = psDevInfo->uiFBDevID;
 
-       
+       /* Link the buffers */
        for(i=0; i<ui32BufferCount-1; i++)
        {
                psBuffer[i].psNext = &psBuffer[i+1];
        }
-       
+       /* and link last to first */
        psBuffer[i].psNext = &psBuffer[0];
 
-       
+       /* Configure the swapchain buffers */
        for(i=0; i<ui32BufferCount; i++)
        {
                IMG_UINT32 ui32SwapBuffer = i + ui32BuffersToSkip;
                IMG_UINT32 ui32BufferOffset = ui32SwapBuffer * (IMG_UINT32)psDevInfo->sFBInfo.ulRoundedBufferSize;
 
+#if defined(CONFIG_DSSCOMP)
+               if (psDevInfo->sFBInfo.bIs2D)
+               {
+                       ui32BufferOffset = 0;
+               }
+#endif /* defined(CONFIG_DSSCOMP) */
+
                psBuffer[i].psSyncData = ppsSyncData[i];
 
                psBuffer[i].sSysAddr.uiAddr = psDevInfo->sFBInfo.sSysAddr.uiAddr + ui32BufferOffset;
@@ -472,6 +616,14 @@ static PVRSRV_ERROR CreateDCSwapChain(IMG_HANDLE hDevice,
                psBuffer[i].ulYOffset = ui32BufferOffset / psDevInfo->sFBInfo.ulByteStride;
                psBuffer[i].psDevInfo = psDevInfo;
 
+#if defined(CONFIG_DSSCOMP)
+               if (psDevInfo->sFBInfo.bIs2D)
+               {
+                       psBuffer[i].sSysAddr.uiAddr += ui32SwapBuffer *
+                               ALIGN((IMG_UINT32)psDevInfo->sFBInfo.ulWidth * psDevInfo->sFBInfo.uiBytesPerPixel, PAGE_SIZE);
+               }
+#endif /* defined(CONFIG_DSSCOMP) */
+
                OMAPLFBInitBufferForSwap(&psBuffer[i]);
        }
 
@@ -517,6 +669,10 @@ ExitUnLock:
        return eError;
 }
 
+/*
+ * DestroyDCSwapChain
+ * Called from services.
+ */
 static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
        IMG_HANDLE hSwapChain)
 {
@@ -524,7 +680,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
        OMAPLFB_SWAPCHAIN *psSwapChain;
        OMAPLFB_ERROR eError;
 
-       
+       /* Check parameters */
        if(!hDevice || !hSwapChain)
        {
                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -544,7 +700,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
                goto ExitUnLock;
        }
 
-       
+       /* The swap queue is flushed before being destroyed */
        OMAPLFBDestroySwapQueue(psSwapChain);
 
        eError = OMAPLFBDisableLFBEventNotification(psDevInfo);
@@ -553,7 +709,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(IMG_HANDLE hDevice,
                printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't disable framebuffer event notification\n", __FUNCTION__, psDevInfo->uiFBDevID);
        }
 
-       
+       /* Free resources */
        OMAPLFBFreeKernelMem(psSwapChain->psBuffer);
        OMAPLFBFreeKernelMem(psSwapChain);
 
@@ -570,6 +726,10 @@ ExitUnLock:
        return eError;
 }
 
+/*
+ * SetDCDstRect
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCDstRect(IMG_HANDLE hDevice,
        IMG_HANDLE hSwapChain,
        IMG_RECT *psRect)
@@ -578,11 +738,15 @@ static PVRSRV_ERROR SetDCDstRect(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(psRect);
 
-       
+       /* Only full display swapchains on this device */
        
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCSrcRect
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCSrcRect(IMG_HANDLE hDevice,
                                  IMG_HANDLE hSwapChain,
                                  IMG_RECT *psRect)
@@ -591,11 +755,15 @@ static PVRSRV_ERROR SetDCSrcRect(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(psRect);
 
-       
+       /* Only full display swapchains on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCDstColourKey
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCDstColourKey(IMG_HANDLE hDevice,
                                       IMG_HANDLE hSwapChain,
                                       IMG_UINT32 ui32CKColour)
@@ -604,11 +772,15 @@ static PVRSRV_ERROR SetDCDstColourKey(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(ui32CKColour);
 
-       
+       /* Don't support DST CK on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * SetDCSrcColourKey
+ * Called from services.
+ */
 static PVRSRV_ERROR SetDCSrcColourKey(IMG_HANDLE hDevice,
                                       IMG_HANDLE hSwapChain,
                                       IMG_UINT32 ui32CKColour)
@@ -617,11 +789,15 @@ static PVRSRV_ERROR SetDCSrcColourKey(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(hSwapChain);
        UNREFERENCED_PARAMETER(ui32CKColour);
 
-       
+       /* Don't support SRC CK on this device */
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
 
+/*
+ * GetDCBuffers
+ * Called from services.
+ */
 static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
                                  IMG_HANDLE hSwapChain,
                                  IMG_UINT32 *pui32BufferCount,
@@ -632,7 +808,7 @@ static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
        PVRSRV_ERROR eError;
        unsigned i;
        
-       
+       /* Check parameters */
        if(!hDevice 
        || !hSwapChain
        || !pui32BufferCount
@@ -655,10 +831,10 @@ static PVRSRV_ERROR GetDCBuffers(IMG_HANDLE hDevice,
                goto Exit;
        }
        
-       
+       /* Return the buffer count */
        *pui32BufferCount = (IMG_UINT32)psSwapChain->ulBufferCount;
        
-       
+       /* Return the buffers */
        for(i=0; i<psSwapChain->ulBufferCount; i++)
        {
                phBuffer[i] = (IMG_HANDLE)&psSwapChain->psBuffer[i];
@@ -672,6 +848,10 @@ Exit:
        return eError;
 }
 
+/*
+ * SwapToDCBuffer
+ * Called from services.
+ */
 static PVRSRV_ERROR SwapToDCBuffer(IMG_HANDLE hDevice,
                                    IMG_HANDLE hBuffer,
                                    IMG_UINT32 ui32SwapInterval,
@@ -686,21 +866,17 @@ static PVRSRV_ERROR SwapToDCBuffer(IMG_HANDLE hDevice,
        UNREFERENCED_PARAMETER(ui32ClipRectCount);
        UNREFERENCED_PARAMETER(psClipRect);
        
-       
+       /* * Nothing to do since Services common code does the work */
 
        return PVRSRV_OK;
 }
 
-static PVRSRV_ERROR SwapToDCSystem(IMG_HANDLE hDevice,
-                                   IMG_HANDLE hSwapChain)
-{
-       UNREFERENCED_PARAMETER(hDevice);
-       UNREFERENCED_PARAMETER(hSwapChain);
-       
-       
-       return PVRSRV_OK;
-}
-
+/*
+ * Called after the screen has unblanked, or after any other occasion
+ * when we didn't wait for vsync, but now need to. Not doing this after
+ * unblank leads to screen jitter on some screens.
+ * Returns true if the screen has been deemed to have settled.
+ */
 static OMAPLFB_BOOL WaitForVSyncSettle(OMAPLFB_DEVINFO *psDevInfo)
 {
                unsigned i;
@@ -715,6 +891,14 @@ static OMAPLFB_BOOL WaitForVSyncSettle(OMAPLFB_DEVINFO *psDevInfo)
                return OMAPLFB_TRUE;
 }
 
+/*
+ * Swap handler.
+ * Called from the swap chain work queue handler.
+ * There is no need to take the swap chain creation lock in here, or use
+ * some other method of stopping the swap chain from being destroyed.
+ * This is because the swap chain creation lock is taken when queueing work,
+ * and the work queue is flushed before the swap chain is destroyed.
+ */
 void OMAPLFBSwapHandler(OMAPLFB_BUFFER *psBuffer)
 {
        OMAPLFB_DEVINFO *psDevInfo = psBuffer->psDevInfo;
@@ -767,57 +951,245 @@ void OMAPLFBSwapHandler(OMAPLFB_BUFFER *psBuffer)
        psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete((IMG_HANDLE)psBuffer->hCmdComplete, IMG_TRUE);
 }
 
+/* Triggered by PVRSRVSwapToDCBuffer */
+static IMG_BOOL ProcessFlipV1(IMG_HANDLE hCmdCookie,
+                                                         OMAPLFB_DEVINFO *psDevInfo,
+                                                         OMAPLFB_SWAPCHAIN *psSwapChain,
+                                                         OMAPLFB_BUFFER *psBuffer,
+                                                         unsigned long ulSwapInterval)
+{
+       OMAPLFBCreateSwapChainLock(psDevInfo);
+
+       /* The swap chain has been destroyed */
+       if (SwapChainHasChanged(psDevInfo, psSwapChain))
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX
+                       ": %s: Device %u (PVR Device ID %u): The swap chain has been destroyed\n",
+                       __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
+       }
+       else
+       {
+               psBuffer->hCmdComplete = (OMAPLFB_HANDLE)hCmdCookie;
+               psBuffer->ulSwapInterval = ulSwapInterval;
+#if defined(CONFIG_DSSCOMP)
+               if (is_tiler_addr(psBuffer->sSysAddr.uiAddr))
+               {
+                       IMG_UINT32 w = psBuffer->psDevInfo->sDisplayDim.ui32Width;
+                       IMG_UINT32 h = psBuffer->psDevInfo->sDisplayDim.ui32Height;
+                       struct dsscomp_setup_dispc_data comp = {
+                               .num_mgrs = 1,
+                               .mgrs[0].alpha_blending = 1,
+                               .num_ovls = 1,
+                               .ovls[0].cfg =
+                               {
+                                       .width = w,
+                                       .win.w = w,
+                                       .crop.w = w,
+                                       .height = h,
+                                       .win.h = h,
+                                       .crop.h = h,
+                                       .stride = psBuffer->psDevInfo->sDisplayDim.ui32ByteStride,
+                                       .color_mode = OMAP_DSS_COLOR_ARGB32,
+                                       .enabled = 1,
+                                       .global_alpha = 255,
+                               },
+                               .mode = DSSCOMP_SETUP_DISPLAY,
+                       };
+                       struct tiler_pa_info *pas[1] = { NULL };
+                       comp.ovls[0].ba = (u32) psBuffer->sSysAddr.uiAddr;
+                       dsscomp_gralloc_queue(&comp, pas, true,
+                                                                 (void *) psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete,
+                                                                 (void *) psBuffer->hCmdComplete);
+               }
+               else
+#endif /* defined(CONFIG_DSSCOMP) */
+               {
+                       OMAPLFBQueueBufferForSwap(psSwapChain, psBuffer);
+               }
+       }
+
+       OMAPLFBCreateSwapChainUnLock(psDevInfo);
+
+       return IMG_TRUE;
+}
+
+#if defined(CONFIG_DSSCOMP)
+
+/* Triggered by PVRSRVSwapToDCBuffer2 */
+static IMG_BOOL ProcessFlipV2(IMG_HANDLE hCmdCookie,
+                                                         OMAPLFB_DEVINFO *psDevInfo,
+                                                         PDC_MEM_INFO *ppsMemInfos,
+                                                         IMG_UINT32 ui32NumMemInfos,
+                                                         struct dsscomp_setup_dispc_data *psDssData,
+                                                         IMG_UINT32 ui32DssDataLength)
+{
+       struct tiler_pa_info *apsTilerPAs[5];
+       IMG_UINT32 i, k;
+
+       if(ui32DssDataLength != sizeof(*psDssData))
+       {
+               WARN(1, "invalid size of private data (%d vs %d)",
+                        ui32DssDataLength, sizeof(*psDssData));
+               return IMG_FALSE;
+       }
+
+       if(psDssData->num_ovls == 0 || ui32NumMemInfos == 0)
+       {
+               WARN(1, "must have at least one layer");
+               return IMG_FALSE;
+       }
+
+       for(i = k = 0; i < ui32NumMemInfos && k < ARRAY_SIZE(apsTilerPAs); i++, k++)
+       {
+               struct tiler_pa_info *psTilerInfo;
+               IMG_CPU_VIRTADDR virtAddr;
+               IMG_CPU_PHYADDR phyAddr;
+               IMG_UINT32 ui32NumPages;
+               IMG_SIZE_T uByteSize;
+               int j;
+
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetByteSize(ppsMemInfos[i], &uByteSize);
+               ui32NumPages = (uByteSize + PAGE_SIZE - 1) >> PAGE_SHIFT;
+
+               apsTilerPAs[k] = NULL;
+
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], 0, &phyAddr);
+
+               /* NV12 buffers are already mapped to tiler */
+               if(psDssData->ovls[k].cfg.color_mode == OMAP_DSS_COLOR_NV12)
+               {
+                       psDssData->ovls[k].ba = (u32)phyAddr.uiAddr;
+
+                       psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], (uByteSize * 2) / 3, &phyAddr);
+                       psDssData->ovls[k].uv = (u32)phyAddr.uiAddr;
+                       continue;
+               }
+
+               /* Other kinds of buffer may also already be mapped to tiler */
+               if(is_tiler_addr((u32)phyAddr.uiAddr))
+               {
+                       psDssData->ovls[k].ba = (u32)phyAddr.uiAddr;
+                       continue;
+               }
+
+               psTilerInfo = kzalloc(sizeof(*psTilerInfo), GFP_KERNEL);
+               if(!psTilerInfo)
+               {
+                       continue;
+               }
+
+               psTilerInfo->mem = kzalloc(sizeof(*psTilerInfo->mem) * ui32NumPages, GFP_KERNEL);
+               if(!psTilerInfo->mem)
+               {
+                       kfree(psTilerInfo);
+                       continue;
+               }
+
+               psTilerInfo->num_pg = ui32NumPages;
+               psTilerInfo->memtype = TILER_MEM_USING;
+
+               for(j = 0; j < ui32NumPages; j++)
+               {
+                       psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuPAddr(ppsMemInfos[i], j << PAGE_SHIFT, &phyAddr);
+                       psTilerInfo->mem[j] = (u32)phyAddr.uiAddr;
+               }
+
+               /* Need base address for in-page offset */
+               psDevInfo->sPVRJTable.pfnPVRSRVDCMemInfoGetCpuVAddr(ppsMemInfos[i], &virtAddr);
+               psDssData->ovls[k].ba = (u32)virtAddr;
+               apsTilerPAs[k] = psTilerInfo;
+       }
+
+       /* Set up cloned layer addresses (but don't duplicate tiler_pas) */
+       for(i = k; i < psDssData->num_ovls && i < ARRAY_SIZE(apsTilerPAs); i++)
+       {
+               unsigned int ix = psDssData->ovls[i].ba;
+               if(ix >= ARRAY_SIZE(apsTilerPAs))
+               {
+                       WARN(1, "Invalid clone layer (%u); skipping all cloned layers", ix);
+                       psDssData->num_ovls = k;
+                       break;
+               }
+               apsTilerPAs[i] = apsTilerPAs[ix];
+               psDssData->ovls[i].ba = psDssData->ovls[ix].ba;
+               psDssData->ovls[i].uv = psDssData->ovls[ix].uv;
+       }
+
+       dsscomp_gralloc_queue(psDssData, apsTilerPAs, false,
+                                                 (void *)psDevInfo->sPVRJTable.pfnPVRSRVCmdComplete,
+                                                 (void *)hCmdCookie);
+
+       for(i = 0; i < k; i++)
+       {
+               tiler_pa_free(apsTilerPAs[i]);
+       }
+
+       return IMG_TRUE;
+}
+
+#endif /* defined(CONFIG_DSSCOMP) */
+
+/* Command processing flip handler function.  Called from services. */
 static IMG_BOOL ProcessFlip(IMG_HANDLE  hCmdCookie,
                             IMG_UINT32  ui32DataSize,
                             IMG_VOID   *pvData)
 {
        DISPLAYCLASS_FLIP_COMMAND *psFlipCmd;
        OMAPLFB_DEVINFO *psDevInfo;
-       OMAPLFB_BUFFER *psBuffer;
-       OMAPLFB_SWAPCHAIN *psSwapChain;
 
-       
+       /* Check parameters  */
        if(!hCmdCookie || !pvData)
        {
                return IMG_FALSE;
        }
 
-       
+       /* Validate data packet  */
        psFlipCmd = (DISPLAYCLASS_FLIP_COMMAND*)pvData;
 
-       if (psFlipCmd == IMG_NULL || sizeof(DISPLAYCLASS_FLIP_COMMAND) != ui32DataSize)
+       if (psFlipCmd == IMG_NULL)
        {
                return IMG_FALSE;
        }
 
-       
        psDevInfo = (OMAPLFB_DEVINFO*)psFlipCmd->hExtDevice;
-       psBuffer = (OMAPLFB_BUFFER*)psFlipCmd->hExtBuffer;
-       psSwapChain = (OMAPLFB_SWAPCHAIN*) psFlipCmd->hExtSwapChain;
-
-       OMAPLFBCreateSwapChainLock(psDevInfo);
 
-       if (SwapChainHasChanged(psDevInfo, psSwapChain))
+       if(psFlipCmd->hExtBuffer)
        {
-               
-               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX
-                       ": %s: Device %u (PVR Device ID %u): The swap chain has been destroyed\n",
-                       __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
+               return ProcessFlipV1(hCmdCookie,
+                                                        psDevInfo,
+                                                        psFlipCmd->hExtSwapChain,
+                                                        psFlipCmd->hExtBuffer,
+                                                        psFlipCmd->ui32SwapInterval);
        }
        else
        {
-               psBuffer->hCmdComplete = (OMAPLFB_HANDLE)hCmdCookie;
-               psBuffer->ulSwapInterval = (unsigned long)psFlipCmd->ui32SwapInterval;
-
-               OMAPLFBQueueBufferForSwap(psSwapChain, psBuffer);
+#if defined(CONFIG_DSSCOMP)
+               DISPLAYCLASS_FLIP_COMMAND2 *psFlipCmd2;
+               psFlipCmd2 = (DISPLAYCLASS_FLIP_COMMAND2 *)pvData;
+               return ProcessFlipV2(hCmdCookie,
+                                                        psDevInfo,
+                                                        psFlipCmd2->ppsMemInfos,
+                                                        psFlipCmd2->ui32NumMemInfos,
+                                                        psFlipCmd2->pvPrivData,
+                                                        psFlipCmd2->ui32PrivDataLength);
+#else
+               BUG();
+#endif
        }
+}
 
-       OMAPLFBCreateSwapChainUnLock(psDevInfo);
+/*!
+******************************************************************************
 
-       return IMG_TRUE;
-}
+ @Function     OMAPLFBInitFBDev
+ @Description specifies devices in the systems memory map
+ @Input    psSysData - sys data
 
+ @Return   OMAPLFB_ERROR  :
 
+******************************************************************************/
 static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
 {
        struct fb_info *psLINFBInfo;
@@ -828,11 +1200,7 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        unsigned long ulLCM;
        unsigned uiFBDevID = psDevInfo->uiFBDevID;
 
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-        acquire_console_sem();
-#endif
+       OMAPLFB_CONSOLE_LOCK();
 
        psLINFBInfo = registered_fb[uiFBDevID];
        if (psLINFBInfo == NULL)
@@ -845,7 +1213,10 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
                                        psLINFBInfo->screen_size :
                                        psLINFBInfo->fix.smem_len;
 
-       
+       /*
+        * Try and filter out invalid FB info structures (a problem
+        * seen on some OMAP3 systems).
+        */
        if (FBSize == 0 || psLINFBInfo->fix.line_length == 0)
        {
                eError = OMAPLFB_ERROR_INVALID_DEVICE;
@@ -907,7 +1278,87 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
                        ": Device %u: LCM of stride and page size: %lu\n",
                        psDevInfo->uiFBDevID, ulLCM));
 
-       
+       /* Additional implementation specific information */
+       OMAPLFBPrintInfo(psDevInfo);
+
+#if defined(CONFIG_DSSCOMP)
+       {
+               /* for some reason we need at least 3 buffers in the swap chain */
+               int n = FBSize / RoundUpToMultiple(psLINFBInfo->fix.line_length * psLINFBInfo->var.yres, ulLCM);
+               int res;
+               int i, x, y, w;
+               ion_phys_addr_t phys;
+               size_t size;
+               struct tiler_view_t view;
+
+               struct omap_ion_tiler_alloc_data sAllocData =
+               {
+                       /* TILER will align width to 128-bytes */
+                       /* however, SGX must have full page width */
+                       .w = ALIGN(psLINFBInfo->var.xres, PAGE_SIZE / (psLINFBInfo->var.bits_per_pixel / 8)),
+                       .h = psLINFBInfo->var.yres,
+                       .fmt = psLINFBInfo->var.bits_per_pixel == 16 ? TILER_PIXEL_FMT_16BIT : TILER_PIXEL_FMT_32BIT,
+                       .flags = 0,
+               };
+
+               printk(KERN_DEBUG DRIVER_PREFIX
+                          " %s: Device %u: Requesting %d TILER 2D framebuffers\n",
+                          __FUNCTION__, uiFBDevID, n);
+
+               /* INTEGRATION_POINT: limit to MAX 3 FBs to save TILER container space */
+               if (n > 3)
+                       n = 3;
+
+               sAllocData.w *= n;
+
+               psPVRFBInfo->uiBytesPerPixel = psLINFBInfo->var.bits_per_pixel >> 3;
+               psPVRFBInfo->bIs2D = OMAPLFB_TRUE;
+
+               res = omap_ion_tiler_alloc(gpsIONClient, &sAllocData);
+               psPVRFBInfo->psIONHandle = sAllocData.handle;
+               if (res < 0)
+               {
+                       printk(KERN_ERR DRIVER_PREFIX
+                                  " %s: Device %u: Could not allocate 2D framebuffer(%d)\n",
+                                  __FUNCTION__, uiFBDevID, res);
+                       goto ErrorModPut;
+               }
+
+               psLINFBInfo->fix.smem_start = ion_phys(gpsIONClient, sAllocData.handle, &phys, &size);
+
+               psPVRFBInfo->sSysAddr.uiAddr = phys;
+               psPVRFBInfo->sCPUVAddr = 0;
+               psPVRFBInfo->ulWidth = psLINFBInfo->var.xres;
+               psPVRFBInfo->ulHeight = psLINFBInfo->var.yres;
+
+               psPVRFBInfo->ulByteStride = PAGE_ALIGN(psPVRFBInfo->ulWidth * psPVRFBInfo->uiBytesPerPixel);
+               w = psPVRFBInfo->ulByteStride >> PAGE_SHIFT;
+               /* this is an "effective" FB size to get correct number of buffers */
+               psPVRFBInfo->ulFBSize = sAllocData.h * n * psPVRFBInfo->ulByteStride;
+               psPVRFBInfo->psPageList = kzalloc(w * n * psPVRFBInfo->ulHeight * sizeof(*psPVRFBInfo->psPageList), GFP_KERNEL);
+               if (!psPVRFBInfo->psPageList)
+               {
+                       printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Could not allocate page list\n", __FUNCTION__, psDevInfo->uiFBDevID);
+                       ion_free(gpsIONClient, sAllocData.handle);
+                       goto ErrorModPut;
+               }
+
+               tilview_create(&view, phys, psDevInfo->sFBInfo.ulWidth, psDevInfo->sFBInfo.ulHeight);
+               for(i = 0; i < n; i++)
+               {
+                       for(y = 0; y < psDevInfo->sFBInfo.ulHeight; y++)
+                       {
+                               for(x = 0; x < w; x++)
+                               {
+                                       psPVRFBInfo->psPageList[i * psDevInfo->sFBInfo.ulHeight * w + y * w + x].uiAddr =
+                                       phys + view.v_inc * y + ((x + i * w) << PAGE_SHIFT);
+                               }
+                       }
+               }
+       }
+#else /* defined(CONFIG_DSSCOMP) */
+       /* System Surface */
        psPVRFBInfo->sSysAddr.uiAddr = psLINFBInfo->fix.smem_start;
        psPVRFBInfo->sCPUVAddr = psLINFBInfo->screen_base;
 
@@ -915,8 +1366,15 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        psPVRFBInfo->ulHeight = psLINFBInfo->var.yres;
        psPVRFBInfo->ulByteStride =  psLINFBInfo->fix.line_length;
        psPVRFBInfo->ulFBSize = FBSize;
+#endif /* defined(CONFIG_DSSCOMP) */
+
        psPVRFBInfo->ulBufferSize = psPVRFBInfo->ulHeight * psPVRFBInfo->ulByteStride;
-       
+
+       /* Round the buffer size up to a multiple of the number of pages
+        * and the byte stride.
+        * This is used internally, to ensure buffers start on page
+        * boundaries, for the benefit of PVR Services.
+        */
        psPVRFBInfo->ulRoundedBufferSize = RoundUpToMultiple(psPVRFBInfo->ulBufferSize, ulLCM);
 
        if(psLINFBInfo->var.bits_per_pixel == 16)
@@ -964,7 +1422,7 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        psDevInfo->sFBInfo.ulPhysicalHeightmm =
                ((int)psLINFBInfo->var.height > 0) ? psLINFBInfo->var.height : 54;
 
-       
+       /* System Surface */
        psDevInfo->sFBInfo.sSysAddr.uiAddr = psPVRFBInfo->sSysAddr.uiAddr;
        psDevInfo->sFBInfo.sCPUVAddr = psPVRFBInfo->sCPUVAddr;
 
@@ -974,11 +1432,8 @@ static OMAPLFB_ERROR OMAPLFBInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
 ErrorModPut:
        module_put(psLINFBOwner);
 ErrorRelSem:
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-        release_console_sem();
-#endif
+       OMAPLFB_CONSOLE_UNLOCK();
+
        return eError;
 }
 
@@ -987,11 +1442,18 @@ static void OMAPLFBDeInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        struct fb_info *psLINFBInfo = psDevInfo->psLINFBInfo;
        struct module *psLINFBOwner;
 
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-        acquire_console_sem();
-#endif
+       OMAPLFB_CONSOLE_LOCK();
+
+#if defined(CONFIG_DSSCOMP)
+       {
+               OMAPLFB_FBINFO *psPVRFBInfo = &psDevInfo->sFBInfo;
+               kfree(psPVRFBInfo->psPageList);
+               if (psPVRFBInfo->psIONHandle)
+               {
+                       ion_free(gpsIONClient, psPVRFBInfo->psIONHandle);
+               }
+       }
+#endif /* defined(CONFIG_DSSCOMP) */
 
        psLINFBOwner = psLINFBInfo->fbops->owner;
 
@@ -1001,11 +1463,8 @@ static void OMAPLFBDeInitFBDev(OMAPLFB_DEVINFO *psDevInfo)
        }
 
        module_put(psLINFBOwner);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-        release_console_sem();
-#endif
+
+       OMAPLFB_CONSOLE_UNLOCK();
 }
 
 static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
@@ -1014,7 +1473,7 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
        IMG_UINT32              aui32SyncCountList[OMAPLFB_COMMAND_COUNT][2];
        OMAPLFB_DEVINFO         *psDevInfo = NULL;
 
-       
+       /* Allocate device info. structure */
        psDevInfo = (OMAPLFB_DEVINFO *)OMAPLFBAllocKernelMem(sizeof(OMAPLFB_DEVINFO));
 
        if(psDevInfo == NULL)
@@ -1025,21 +1484,26 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                goto ErrorExit;
        }
 
-       
+       /* Any fields not set will be zero */
        memset(psDevInfo, 0, sizeof(OMAPLFB_DEVINFO));
 
        psDevInfo->uiFBDevID = uiFBDevID;
 
-       
+       /* Get the kernel services function table */
        if(!(*gpfnGetPVRJTable)(&psDevInfo->sPVRJTable))
        {
                goto ErrorFreeDevInfo;
        }
 #ifdef FBDEV_PRESENT
-       
+       /* Save private fbdev information structure in the dev. info. */
        if(OMAPLFBInitFBDev(psDevInfo) != OMAPLFB_OK)
        {
-               
+               /*
+                * Leave it to OMAPLFBInitFBDev to print an error message, if
+                * required.  The function may have failed because
+                * there is no Linux framebuffer device corresponding
+                * to the device ID.
+                */
                goto ErrorFreeDevInfo;
        }
 
@@ -1064,14 +1528,14 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                ": Device %u: Maximum number of swap chain buffers: %u\n",
                psDevInfo->uiFBDevID, psDevInfo->sDisplayInfo.ui32MaxSwapChainBuffers));
 
-       
+       /* Setup system buffer */
        psDevInfo->sSystemBuffer.sSysAddr = psDevInfo->sFBInfo.sSysAddr;
        psDevInfo->sSystemBuffer.sCPUVAddr = psDevInfo->sFBInfo.sCPUVAddr;
        psDevInfo->sSystemBuffer.psDevInfo = psDevInfo;
 
        OMAPLFBInitBufferForSwap(&psDevInfo->sSystemBuffer);
 #else
-                psDevInfo->sSystemBuffer.sCPUVAddr = 0x100;
+psDevInfo->sSystemBuffer.sCPUVAddr = 0x100;
 //                psDevInfo->sSystemBuffer.ulBufferSize = 600*3200;
 
                 psDevInfo->sDisplayFormat.pixelformat = 20;
@@ -1083,6 +1547,9 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
 #endif
 
 
+       /*
+               Setup the DC Jtable so SRVKM can call into this driver
+       */
        psDevInfo->sDCJTable.ui32TableSize = sizeof(PVRSRV_DC_SRV2DISP_KMJTABLE);
        psDevInfo->sDCJTable.pfnOpenDCDevice = OpenDCDevice;
        psDevInfo->sDCJTable.pfnCloseDCDevice = CloseDCDevice;
@@ -1099,10 +1566,9 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
        psDevInfo->sDCJTable.pfnSetDCSrcColourKey = SetDCSrcColourKey;
        psDevInfo->sDCJTable.pfnGetDCBuffers = GetDCBuffers;
        psDevInfo->sDCJTable.pfnSwapToDCBuffer = SwapToDCBuffer;
-       psDevInfo->sDCJTable.pfnSwapToDCSystem = SwapToDCSystem;
        psDevInfo->sDCJTable.pfnSetDCState = SetDCState;
 
-       
+       /* Register device with services and retrieve device index */
        if(psDevInfo->sPVRJTable.pfnPVRSRVRegisterDCDevice(
                &psDevInfo->sDCJTable,
                &psDevInfo->uiPVRDevID) != PVRSRV_OK)
@@ -1116,17 +1582,18 @@ static OMAPLFB_DEVINFO *OMAPLFBInitDev(unsigned uiFBDevID)
                ": Device %u: PVR Device ID: %u\n",
                psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID));
        
-       
+       /* Setup private command processing function table ... */
        pfnCmdProcList[DC_FLIP_COMMAND] = ProcessFlip;
 
-       
-       aui32SyncCountList[DC_FLIP_COMMAND][0] = 0; 
-       aui32SyncCountList[DC_FLIP_COMMAND][1] = 2; 
-
-       
-
-
+       /* ... and associated sync count(s) */
+       aui32SyncCountList[DC_FLIP_COMMAND][0] = 0; /* writes */
+       aui32SyncCountList[DC_FLIP_COMMAND][1] = 10; /* reads */
 
+       /*
+               Register private command processing functions with
+               the Command Queue Manager and setup the general
+               command complete function in the devinfo.
+       */
        if (psDevInfo->sPVRJTable.pfnPVRSRVRegisterCmdProcList(psDevInfo->uiPVRDevID,
                                                                                                                        &pfnCmdProcList[0],
                                                                                                                        aui32SyncCountList,
@@ -1171,14 +1638,18 @@ OMAPLFB_ERROR OMAPLFBInit(void)
                return OMAPLFB_ERROR_INIT_FAILURE;
        }
 
-       
+       /*
+        * We search for frame buffer devices backwards, as the last device
+        * registered with PVR Services will be the first device enumerated
+        * by PVR Services.
+        */
        for(i = uiMaxFBDevIDPlusOne; i-- != 0;)
        {
                OMAPLFB_DEVINFO *psDevInfo = OMAPLFBInitDev(i);
 
                if (psDevInfo != NULL)
                {
-                       
+                       /* Set the top-level anchor */
                        OMAPLFBSetDevInfoPtr(psDevInfo->uiFBDevID, psDevInfo);
                        uiDevicesFound++;
                }
@@ -1187,6 +1658,10 @@ OMAPLFB_ERROR OMAPLFBInit(void)
        return (uiDevicesFound != 0) ? OMAPLFB_OK : OMAPLFB_ERROR_INIT_FAILURE;
 }
 
+/*
+ *     OMAPLFBDeInitDev
+ *     DeInitialises one device
+ */
 static OMAPLFB_BOOL OMAPLFBDeInitDev(OMAPLFB_DEVINFO *psDevInfo)
 {
        PVRSRV_DC_DISP2SRV_KMJTABLE *psPVRJTable = &psDevInfo->sPVRJTable;
@@ -1211,24 +1686,31 @@ static OMAPLFB_BOOL OMAPLFBDeInitDev(OMAPLFB_DEVINFO *psDevInfo)
                return OMAPLFB_FALSE;
        }
 
-       
+       /*
+        * Remove display class device from kernel services device
+        * register.
+        */
        if (psPVRJTable->pfnPVRSRVRemoveDCDevice(psDevInfo->uiPVRDevID) != PVRSRV_OK)
        {
                printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: PVR Device %u: Couldn't remove device from PVR Services\n", __FUNCTION__, psDevInfo->uiFBDevID, psDevInfo->uiPVRDevID);
                return OMAPLFB_FALSE;
        }
-#ifdef FBDEV_PRESENT   
+       
        OMAPLFBDeInitFBDev(psDevInfo);
-#endif
+
        OMAPLFBSetDevInfoPtr(psDevInfo->uiFBDevID, NULL);
 
-       
+       /* De-allocate data structure */
        OMAPLFBFreeKernelMem(psDevInfo);
 
        return OMAPLFB_TRUE;
 }
 
+/*
+ *     OMAPLFBDeInit
+ *     Deinitialises the display class device component of the FBDev
+ */
 OMAPLFB_ERROR OMAPLFBDeInit(void)
 {
        unsigned uiMaxFBDevIDPlusOne = OMAPLFBMaxFBDevIDPlusOne();
@@ -1248,3 +1730,7 @@ OMAPLFB_ERROR OMAPLFBDeInit(void)
        return (bError) ? OMAPLFB_ERROR_INIT_FAILURE : OMAPLFB_OK;
 }
 
+/******************************************************************************
+ End of file (omaplfb_displayclass.c)
+******************************************************************************/
+
index 74134c6..34669e1 100644 (file)
@@ -1,38 +1,80 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OMAP linux display driver components
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+  
+*/ /**************************************************************************/
+
+/**************************************************************************
+ The 3rd party driver is a specification of an API to integrate the IMG POWERVR
+ Services driver with 3rd Party display hardware.  It is NOT a specification for
+ a display controller driver, rather a specification to extend the API for a
+ pre-existing driver for the display hardware.
+
+ The 3rd party driver interface provides IMG POWERVR client drivers (e.g. PVR2D)
+ with an API abstraction of the system's underlying display hardware, allowing
+ the client drivers to indirectly control the display hardware and access its
+ associated memory.
+ Functions of the API include
+ - query primary surface attributes (width, height, stride, pixel format, CPU
+     physical and virtual address)
+ - swap/flip chain creation and subsequent query of surface attributes
+ - asynchronous display surface flipping, taking account of asynchronous read
+ (flip) and write (render) operations to the display surface
+
+ Note: having queried surface attributes the client drivers are able to map the
+ display memory to any IMG POWERVR Services device by calling
+ PVRSRVMapDeviceClassMemory with the display surface handle.
+
+ This code is intended to be an example of how a pre-existing display driver may
+ be extended to support the 3rd Party Display interface to POWERVR Services
+ - IMG is not providing a display driver implementation.
+ **************************************************************************/
 
 #include <linux/version.h>
 
-#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,38)
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,38))
 #ifndef AUTOCONF_INCLUDED
 #include <linux/config.h>
 #endif
 #endif
 
-
 #include <asm/atomic.h>
 
 #if defined(SUPPORT_DRI_DRM)
 #include <linux/workqueue.h>
 #include <linux/fb.h>
 #include <linux/console.h>
-// #include <linux/omapfb.h>
+#include <linux/omapfb.h>
 #include <linux/mutex.h>
 
 # include <plat/ti81xx-vpss.h>
-# include <plat/vrfb.h>
+#if defined(PVR_OMAPLFB_DRM_FB)
+#include <plat/display.h>
+#include <linux/omap_gpu.h>
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+/* OmapZoom.org OMAP3 2.6.29 kernel tree       - Needs mach/vrfb.h
+ * OmapZoom.org OMAP3 2.6.32 kernel tree       - No additional header required
+ * OmapZoom.org OMAP4 2.6.33 kernel tree       - No additional header required
+ * OmapZoom.org OMAP4 2.6.34 kernel tree       - Needs plat/vrfb.h
+ * Sholes 2.6.32 kernel tree                   - Needs plat/vrfb.h
+ */
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,34))
 #define PVR_OMAPFB3_NEEDS_PLAT_VRFB_H
 #endif
 
 #if defined(PVR_OMAPFB3_NEEDS_PLAT_VRFB_H)
-# include <plat/vrfb.h>
+#include <plat/vrfb.h>
 #else
-# if defined(PVR_OMAPFB3_NEEDS_MACH_VRFB_H)
-#  include <mach/vrfb.h>
-# endif
+#if defined(PVR_OMAPFB3_NEEDS_MACH_VRFB_H)
+#include <mach/vrfb.h>
+#endif
 #endif
 
 #if defined(DEBUG)
 #define        PVR_DEBUG DEBUG
 #undef DEBUG
 #endif
-//#include <omapfb/omapfb.h>
+#include <omapfb/omapfb.h>
 #if defined(DEBUG)
 #undef DEBUG
 #endif
 #define        DEBUG PVR_DEBUG
 #undef PVR_DEBUG
 #endif
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
+
+#if defined(CONFIG_DSSCOMP)
+#include <mach/tiler.h>
+#include <video/dsscomp.h>
+#include <plat/dsscomp.h>
+#endif /* defined(CONFIG_DSSCOMP) */
 
 #include "img_defs.h"
 #include "servicesext.h"
 #include "3rdparty_dc_drm_shared.h"
 #endif
 
-#if 0
 #if !defined(PVR_LINUX_USING_WORKQUEUES)
 #error "PVR_LINUX_USING_WORKQUEUES must be defined"
 #endif
-#endif
 
 MODULE_SUPPORTED_DEVICE(DEVNAME);
 
-#if 0
+#if !defined(PVR_OMAPLFB_DRM_FB)
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,34))
 #define OMAP_DSS_DRIVER(drv, dev) struct omap_dss_driver *drv = (dev) != NULL ? (dev)->driver : NULL
 #define OMAP_DSS_MANAGER(man, dev) struct omap_overlay_manager *man = (dev) != NULL ? (dev)->manager : NULL
@@ -106,7 +162,7 @@ MODULE_SUPPORTED_DEVICE(DEVNAME);
 #define OMAP_DSS_MANAGER(man, dev) struct omap_dss_device *man = (dev)
 #define        WAIT_FOR_VSYNC(man)     ((man)->wait_vsync)
 #endif
-#endif
+#endif /* !defined(PVR_OMAPLFB_DRM_FB) */
 
 void *OMAPLFBAllocKernelMem(unsigned long ulSize)
 {
@@ -188,12 +244,13 @@ OMAPLFB_ERROR OMAPLFBGetLibFuncAddr (char *szFunctionName, PFN_DC_GET_PVRJTABLE
                return (OMAPLFB_ERROR_INVALID_PARAMS);
        }
 
-       
+       /* Nothing to do - should be exported from pvrsrv.ko */
        *ppfnFuncTable = PVRGetDisplayClassJTable;
 
        return (OMAPLFB_OK);
 }
 
+/* Inset a swap buffer into the swap chain work queue */
 void OMAPLFBQueueBufferForSwap(OMAPLFB_SWAPCHAIN *psSwapChain, OMAPLFB_BUFFER *psBuffer)
 {
        int res = queue_work(psSwapChain->psWorkQueue, &psBuffer->sWork);
@@ -204,6 +261,7 @@ void OMAPLFBQueueBufferForSwap(OMAPLFB_SWAPCHAIN *psSwapChain, OMAPLFB_BUFFER *p
        }
 }
 
+/* Process an item on a swap chain work queue */
 static void WorkQueueHandler(struct work_struct *psWork)
 {
        OMAPLFB_BUFFER *psBuffer = container_of(psWork, OMAPLFB_BUFFER, sWork);
@@ -211,16 +269,42 @@ static void WorkQueueHandler(struct work_struct *psWork)
        OMAPLFBSwapHandler(psBuffer);
 }
 
+/* Create a swap chain work queue */
 OMAPLFB_ERROR OMAPLFBCreateSwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
 {
-#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,34))
-        psSwapChain->psWorkQueue = __create_workqueue(DEVNAME, 1, 1, 1);
-#else  
-       psSwapChain->psWorkQueue = create_workqueue(DEVNAME);
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37))
+       /*
+        * Calling alloc_ordered_workqueue with the WQ_FREEZABLE and
+        * WQ_MEM_RECLAIM flags set, (currently) has the same effect as
+        * calling create_freezable_workqueue. None of the other WQ
+        * flags are valid. Setting WQ_MEM_RECLAIM should allow the
+        * workqueue to continue to service the swap chain in low memory
+        * conditions, preventing the driver from holding on to
+        * resources longer than it needs to.
+        */
+#if (LINUX_VERSION_CODE == KERNEL_VERSION(2,6,37))
+       psSwapChain->psWorkQueue = alloc_ordered_workqueue(DEVNAME, WQ_FREEZEABLE | WQ_MEM_RECLAIM);
+#else
+       psSwapChain->psWorkQueue = alloc_ordered_workqueue(DEVNAME, WQ_FREEZABLE | WQ_MEM_RECLAIM);
+#endif
+
+#else
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36))
+       psSwapChain->psWorkQueue = create_freezable_workqueue(DEVNAME);
+#else
+       /*
+        * Create a single-threaded, freezable, rt-prio workqueue.
+        * Such workqueues are frozen with user threads when a system
+        * suspends, before driver suspend entry points are called.
+        * This ensures this driver will not call into the Linux
+        * framebuffer driver after the latter is suspended.
+        */
+       psSwapChain->psWorkQueue = __create_workqueue(DEVNAME, 1, 1, 1);
+#endif
 #endif
        if (psSwapChain->psWorkQueue == NULL)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: Device %u: create_singlethreaded_workqueue failed\n", __FUNCTION__, psSwapChain->uiFBDevID);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: Couldn't create workqueue\n", __FUNCTION__, psSwapChain->uiFBDevID);
 
                return (OMAPLFB_ERROR_INIT_FAILURE);
        }
@@ -228,27 +312,26 @@ OMAPLFB_ERROR OMAPLFBCreateSwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
        return (OMAPLFB_OK);
 }
 
+/* Prepare buffer for insertion into a swap chain work queue */
 void OMAPLFBInitBufferForSwap(OMAPLFB_BUFFER *psBuffer)
 {
        INIT_WORK(&psBuffer->sWork, WorkQueueHandler);
 }
 
+/* Destroy a swap chain work queue */
 void OMAPLFBDestroySwapQueue(OMAPLFB_SWAPCHAIN *psSwapChain)
 {
        destroy_workqueue(psSwapChain->psWorkQueue);
 }
 
+/* Flip display to given buffer */
 void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
 {
        struct fb_var_screeninfo sFBVar;
        int res;
        unsigned long ulYResVirtual;
 
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-        acquire_console_sem();
-#endif
+       OMAPLFB_CONSOLE_LOCK();
 
        sFBVar = psDevInfo->psLINFBInfo->var;
 
@@ -257,8 +340,62 @@ void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
 
        ulYResVirtual = psBuffer->ulYOffset + sFBVar.yres;
 
-       
+#if defined(CONFIG_DSSCOMP)
+       {
+               /*
+                * If using DSSCOMP, we need to use dsscomp queuing for normal
+                * framebuffer updates, so that previously used overlays get
+                * automatically disabled, and manager gets dirtied.  We can
+                * do that because DSSCOMP takes ownership of all pipelines on
+                * a manager.
+                */
+               struct fb_fix_screeninfo sFBFix = psDevInfo->psLINFBInfo->fix;
+               struct dsscomp_setup_dispc_data d =
+               {
+                       .num_ovls = 1,
+                       .num_mgrs = 1,
+                       .mgrs[0].alpha_blending = 1,
+                       .ovls[0] =
+                       {
+                               .cfg =
+                               {
+                                       .win.w = sFBVar.xres,
+                                       .win.h = sFBVar.yres,
+                                       .crop.x = sFBVar.xoffset,
+                                       .crop.y = sFBVar.yoffset,
+                                       .crop.w = sFBVar.xres,
+                                       .crop.h = sFBVar.yres,
+                                       .width = sFBVar.xres_virtual,
+                                       .height = sFBVar.yres_virtual,
+                                       .stride = sFBFix.line_length,
+                                       .enabled = 1,
+                                       .global_alpha = 255,
+                               },
+                       },
+               };
+
+               /* do not map buffer into TILER1D as it is contiguous */
+               struct tiler_pa_info *pas[] = { NULL };
+
+               d.ovls[0].ba = sFBFix.smem_start;
+               omapfb_mode_to_dss_mode(&sFBVar, &d.ovls[0].cfg.color_mode);
+
+               res = dsscomp_gralloc_queue(&d, pas, true, NULL, NULL);
+       }
+#else /* defined(CONFIG_DSSCOMP) */
+       /*
+        * PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY should be defined to work
+        * around flipping problems seen with the Taal LCDs on Blaze.
+        * The work around is safe to use with other types of screen on Blaze
+        * (e.g. HDMI) and on other platforms (e.g. Panda board).
+        */
+#if !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY)
+       /*
+        * Attempt to change the virtual screen resolution if it is too
+        * small.  Note that fb_set_var also pans the display.
+        */
        if (sFBVar.xres_virtual != sFBVar.xres || sFBVar.yres_virtual < ulYResVirtual)
+#endif /* !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY) */
        {
                sFBVar.xres_virtual = sFBVar.xres;
                sFBVar.yres_virtual = ulYResVirtual;
@@ -268,61 +405,296 @@ void OMAPLFBFlip(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_BUFFER *psBuffer)
                res = fb_set_var(psDevInfo->psLINFBInfo, &sFBVar);
                if (res != 0)
                {
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: fb_set_var failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: fb_set_var failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
                }
        }
+#if !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY)
        else
        {
                res = fb_pan_display(psDevInfo->psLINFBInfo, &sFBVar);
                if (res != 0)
                {
-                        printk (" fb_pan api failed \n");
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: fb_pan_display failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: fb_pan_display failed (Y Offset: %lu, Error: %d)\n", __FUNCTION__, psDevInfo->uiFBDevID, psBuffer->ulYOffset, res);
                }
        }
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-        release_console_sem();
+#endif /* !defined(PVR_OMAPLFB_DONT_USE_FB_PAN_DISPLAY) */
+#endif /* defined(CONFIG_DSSCOMP) */
+
+       OMAPLFB_CONSOLE_UNLOCK();
+}
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3,1,0)
+#if !defined(PVR_OMAPLFB_DRM_FB) || defined(DEBUG)
+static OMAPLFB_BOOL OMAPLFBValidateDSSUpdateMode(enum omap_dss_update_mode eMode)
+{
+       switch (eMode)
+       {
+               case OMAP_DSS_UPDATE_AUTO:
+               case OMAP_DSS_UPDATE_MANUAL:
+               case OMAP_DSS_UPDATE_DISABLED:
+                       return OMAPLFB_TRUE;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_FALSE;
+}
+
+static OMAPLFB_UPDATE_MODE OMAPLFBFromDSSUpdateMode(enum omap_dss_update_mode eMode)
+{
+       switch (eMode)
+       {
+               case OMAP_DSS_UPDATE_AUTO:
+                       return OMAPLFB_UPDATE_MODE_AUTO;
+               case OMAP_DSS_UPDATE_MANUAL:
+                       return OMAPLFB_UPDATE_MODE_MANUAL;
+               case OMAP_DSS_UPDATE_DISABLED:
+                       return OMAPLFB_UPDATE_MODE_DISABLED;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_UPDATE_MODE_UNDEFINED;
+}
+#endif
+#endif
+
+static OMAPLFB_BOOL OMAPLFBValidateUpdateMode(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return OMAPLFB_TRUE;
+               default:
+                       break;
+       }
+
+       return OMAPLFB_FALSE;
+}
+#if 0
+static enum omap_dss_update_mode OMAPLFBToDSSUpdateMode(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+                       return OMAP_DSS_UPDATE_AUTO;
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+                       return OMAP_DSS_UPDATE_MANUAL;
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return OMAP_DSS_UPDATE_DISABLED;
+               default:
+                       break;
+       }
+
+       return -1;
+}
 #endif
+#if defined(DEBUG)
+static const char *OMAPLFBUpdateModeToString(OMAPLFB_UPDATE_MODE eMode)
+{
+       switch(eMode)
+       {
+               case OMAPLFB_UPDATE_MODE_AUTO:
+                       return "Auto Update Mode";
+               case OMAPLFB_UPDATE_MODE_MANUAL:
+                       return "Manual Update Mode";
+               case OMAPLFB_UPDATE_MODE_DISABLED:
+                       return "Update Mode Disabled";
+               case OMAPLFB_UPDATE_MODE_UNDEFINED:
+                       return "Update Mode Undefined";
+               default:
+                       break;
+       }
+
+       return "Unknown Update Mode";
 }
+#if LINUX_VERSION_CODE < KERNEL_VERSION(3,1,0)
+static const char *OMAPLFBDSSUpdateModeToString(enum omap_dss_update_mode eMode)
+{
+
+       if (!OMAPLFBValidateDSSUpdateMode(eMode))
+       {
+               return "Unknown Update Mode";
+       }
+
+       return OMAPLFBUpdateModeToString(OMAPLFBFromDSSUpdateMode(eMode));
+}
+#endif
+void OMAPLFBPrintInfo(OMAPLFB_DEVINFO *psDevInfo)
+{
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       unsigned uConnectors;
+       unsigned uConnector;
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: DRM framebuffer\n", psDevInfo->uiFBDevID));
 
+       for (psConnector = NULL, uConnectors = 0;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               uConnectors++;
+       }
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: Number of screens (DRM connectors): %u\n", psDevInfo->uiFBDevID, uConnectors));
+
+       if (uConnectors == 0)
+       {
+               return;
+       }
+
+       for (psConnector = NULL, uConnector = 0;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL; uConnector++)
+       {
+               enum omap_dss_update_mode eMode = omap_connector_get_update_mode(psConnector);
+
+               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: Screen %u: %s (%d)\n", psDevInfo->uiFBDevID, uConnector, OMAPLFBDSSUpdateModeToString(eMode), (int)eMode));
+
+       }
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+       OMAPLFB_UPDATE_MODE eMode = OMAPLFBGetUpdateMode(psDevInfo);
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: non-DRM framebuffer\n", psDevInfo->uiFBDevID));
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": Device %u: %s\n", psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
+}
+#endif /* defined(DEBUG) */
+
+/* 
+ * Get display update mode.
+ * If the mode is AUTO, we can wait for VSync, if desired.
+ */
 OMAPLFB_UPDATE_MODE OMAPLFBGetUpdateMode(OMAPLFB_DEVINFO *psDevInfo)
 {
 #if 0
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       OMAPLFB_UPDATE_MODE eMode = OMAPLFB_UPDATE_MODE_UNDEFINED;
+
+       /*
+        * There may be multiple displays connected. If at least one
+        * display is manual update mode, report all screens as being
+        * in that mode.
+        */
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               switch(omap_connector_get_update_mode(psConnector))
+               {
+                       case OMAP_DSS_UPDATE_MANUAL:
+                               eMode = OMAPLFB_UPDATE_MODE_MANUAL;
+                               break;
+                       case OMAP_DSS_UPDATE_DISABLED:
+                               if (eMode == OMAPLFB_UPDATE_MODE_UNDEFINED)
+                               {
+                                       eMode = OMAPLFB_UPDATE_MODE_DISABLED;
+                               }
+                               break;
+                       case OMAP_DSS_UPDATE_AUTO:
+                               /* Fall through to default case */
+                       default:
+                               /* Asssume auto update is possible */
+                               if (eMode != OMAPLFB_UPDATE_MODE_MANUAL)
+                               {
+                                       eMode = OMAPLFB_UPDATE_MODE_AUTO;
+                               }
+                               break;
+               }
+       }
+
+       return eMode;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
+
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
 
        enum omap_dss_update_mode eMode;
 
-       if (psDSSDrv == NULL || psDSSDrv->get_update_mode == NULL)
+       if (psDSSDrv == NULL)
        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Can't get update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No DSS device\n", __FUNCTION__, psDevInfo->uiFBDevID));
                return OMAPLFB_UPDATE_MODE_UNDEFINED;
        }
 
-       eMode = psDSSDrv->get_update_mode(psDSSDev);
-       switch(eMode)
+       if (psDSSDrv->get_update_mode == NULL)
        {
-               case OMAP_DSS_UPDATE_AUTO:
+               if (strcmp(psDSSDev->name, "hdmi") == 0)
+               {
+                       return OMAPLFB_UPDATE_MODE_AUTO;
+               }
+//             DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No get_update_mode function\n", __FUNCTION__, psDevInfo->uiFBDevID));
+//             return OMAPLFB_UPDATE_MODE_UNDEFINED;
                        return OMAPLFB_UPDATE_MODE_AUTO;
-               case OMAP_DSS_UPDATE_MANUAL:
-                       return OMAPLFB_UPDATE_MODE_MANUAL;
-               case OMAP_DSS_UPDATE_DISABLED:
-                       return OMAPLFB_UPDATE_MODE_DISABLED;
-               default:
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eMode));
-                       break;
        }
 
-       return OMAPLFB_UPDATE_MODE_UNDEFINED;
+       eMode = psDSSDrv->get_update_mode(psDSSDev);
+       if (!OMAPLFBValidateDSSUpdateMode(eMode))
+       {
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
+       }
+
+       return OMAPLFBFromDSSUpdateMode(eMode);
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 #endif
-        return OMAPLFB_UPDATE_MODE_AUTO;
+return OMAPLFB_UPDATE_MODE_AUTO;
 }
 
+/* Set display update mode */
 OMAPLFB_BOOL OMAPLFBSetUpdateMode(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_UPDATE_MODE eMode)
 {
 #if 0
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+       enum omap_dss_update_mode eDSSMode;
+       OMAPLFB_BOOL bSuccess = OMAPLFB_FALSE;
+       OMAPLFB_BOOL bFailure = OMAPLFB_FALSE;
+
+       if (!OMAPLFBValidateUpdateMode(eMode))
+       {
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
+                       return OMAPLFB_FALSE;
+       }
+       eDSSMode = OMAPLFBToDSSUpdateMode(eMode);
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               int iRes = omap_connector_set_update_mode(psConnector, eDSSMode);
+               OMAPLFB_BOOL bRes = (iRes == 0);
+
+
+               bSuccess |= bRes;
+               bFailure |= !bRes;
+       }
+
+       if (!bFailure)
+       {
+               if (!bSuccess)
+               {
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: No screens\n", __FUNCTION__, psDevInfo->uiFBDevID));
+               }
+
+               return OMAPLFB_TRUE;
+       }
+
+       if (!bSuccess)
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set %s for any screen\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+               return OMAPLFB_FALSE;
+       }
+
+       if (eMode == OMAPLFB_UPDATE_MODE_AUTO)
+       {
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Couldn't set %s for all screens\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+               return OMAPLFB_FALSE;
+       }
+
+       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: %s set for some screens\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBUpdateModeToString(eMode)));
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
        enum omap_dss_update_mode eDSSMode;
@@ -330,41 +702,44 @@ OMAPLFB_BOOL OMAPLFBSetUpdateMode(OMAPLFB_DEVINFO *psDevInfo, OMAPLFB_UPDATE_MOD
 
        if (psDSSDrv == NULL || psDSSDrv->set_update_mode == NULL)
        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Can't set update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Can't set update mode\n", __FUNCTION__, psDevInfo->uiFBDevID));
                return OMAPLFB_FALSE;
        }
 
-       switch(eMode)
+       if (!OMAPLFBValidateUpdateMode(eMode))
        {
-               case OMAPLFB_UPDATE_MODE_AUTO:
-                       eDSSMode = OMAP_DSS_UPDATE_AUTO;
-                       break;
-               case OMAPLFB_UPDATE_MODE_MANUAL:
-                       eDSSMode = OMAP_DSS_UPDATE_MANUAL;
-                       break;
-               case OMAPLFB_UPDATE_MODE_DISABLED:
-                       eDSSMode = OMAP_DSS_UPDATE_DISABLED;
-                       break;
-               default:
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eMode));
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Unknown update mode (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, (int)eMode));
                        return OMAPLFB_FALSE;
        }
+       eDSSMode = OMAPLFBToDSSUpdateMode(eMode);
 
        res = psDSSDrv->set_update_mode(psDSSDev, eDSSMode);
        if (res != 0)
        {
-               DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: set_update_mode failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
+               DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: set_update_mode (%s) failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, OMAPLFBDSSUpdateModeToString(eDSSMode), res));
        }
 
        return (res == 0);
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 #endif
-        return 1;
+return 1;
 }
 
+/* Wait for VSync */
 OMAPLFB_BOOL OMAPLFBWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
 {
-
 #if 0
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL;)
+       {
+               (void) omap_encoder_wait_for_vsync(psConnector->encoder);
+       }
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_MANAGER(psDSSMan, psDSSDev);
 
@@ -373,21 +748,14 @@ OMAPLFB_BOOL OMAPLFBWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
                int res = WAIT_FOR_VSYNC(psDSSMan)(psDSSMan);
                if (res != 0)
                {
-                       DEBUG_PRINTK((KERN_INFO DRIVER_PREFIX ": %s: Device %u: Wait for vsync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
+                       DEBUG_PRINTK((KERN_WARNING DRIVER_PREFIX ": %s: Device %u: Wait for vsync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res));
                        return OMAPLFB_FALSE;
                }
        }
+
+       return OMAPLFB_TRUE;
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
 #endif
-#if 0
-        struct vps_grpx_ctrl *gctrl;
-        int r;
-        gctrl = vps_grpx_get_ctrl(psDevInfo->uiFBDevID); 
-        printk (" BVSYNC \n");
-        r = gctrl->wait_for_vsync(gctrl);
-        printk (" AVSYNC: %d\n", vsync_num++);
-        return OMAPLFB_TRUE;
-#endif
-//    unsigned long timeout = msecs_to_jiffies(500);
 
 #if FBDEV_PRESENT
       int r;
@@ -411,12 +779,33 @@ OMAPLFB_BOOL OMAPLFBWaitForVSync(OMAPLFB_DEVINFO *psDevInfo)
           return OMAPLFB_FALSE;
       }
 #endif
+
       return OMAPLFB_TRUE;
+
 }
 
+/*
+ * Wait for screen to update.  If the screen is in manual or auto update
+ * mode, we can call this function to wait for the screen to update.
+ */
 OMAPLFB_BOOL OMAPLFBManualSync(OMAPLFB_DEVINFO *psDevInfo)
 {
 #if 0
+#if defined(PVR_OMAPLFB_DRM_FB)
+       struct drm_connector *psConnector;
+
+       for (psConnector = NULL;
+               (psConnector = omap_fbdev_get_next_connector(psDevInfo->psLINFBInfo, psConnector)) != NULL; )
+       {
+               /* Try manual sync first, then try wait for vsync */
+               if (omap_connector_sync(psConnector) != 0)
+               {
+                       (void) omap_encoder_wait_for_vsync(psConnector->encoder);
+               }
+       }
+
+       return OMAPLFB_TRUE;
+#else  /* defined(PVR_OMAPLFB_DRM_FB) */
        struct omap_dss_device *psDSSDev = fb2display(psDevInfo->psLINFBInfo);
        OMAP_DSS_DRIVER(psDSSDrv, psDSSDev);
 
@@ -425,15 +814,21 @@ OMAPLFB_BOOL OMAPLFBManualSync(OMAPLFB_DEVINFO *psDevInfo)
                int res = psDSSDrv->sync(psDSSDev);
                if (res != 0)
                {
-                       printk(KERN_INFO DRIVER_PREFIX ": %s: Device %u: Sync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
+                       printk(KERN_ERR DRIVER_PREFIX ": %s: Device %u: Sync failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                        return OMAPLFB_FALSE;
                }
        }
-#endif
 
        return OMAPLFB_TRUE;
+#endif /* defined(PVR_OMAPLFB_DRM_FB) */
+#endif
+return OMAPLFB_TRUE;
 }
 
+/*
+ * If the screen is manual or auto update mode, wait for the screen to
+ * update.
+ */
 OMAPLFB_BOOL OMAPLFBCheckModeAndSync(OMAPLFB_DEVINFO *psDevInfo)
 {
        OMAPLFB_UPDATE_MODE eMode = OMAPLFBGetUpdateMode(psDevInfo);
@@ -450,6 +845,7 @@ OMAPLFB_BOOL OMAPLFBCheckModeAndSync(OMAPLFB_DEVINFO *psDevInfo)
        return OMAPLFB_TRUE;
 }
 
+/* Linux Framebuffer event notification handler */
 static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
                              unsigned long event, void *data)
 {
@@ -458,7 +854,7 @@ static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
        struct fb_info *psFBInfo = psFBEvent->info;
        OMAPLFB_BOOL bBlanked;
 
-       
+       /* Only interested in blanking events */
        if (event != FB_EVENT_BLANK)
        {
                return 0;
@@ -495,47 +891,33 @@ static int OMAPLFBFrameBufferEvents(struct notifier_block *psNotif,
        return 0;
 }
 
+/* Unblank the screen */
 OMAPLFB_ERROR OMAPLFBUnblankDisplay(OMAPLFB_DEVINFO *psDevInfo)
 {
-       int res;
 #ifdef FBDEV_PRESENT
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-        acquire_console_sem();
-#endif
+       int res;
+
+       OMAPLFB_CONSOLE_LOCK();
        res = fb_blank(psDevInfo->psLINFBInfo, 0);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-        release_console_sem();
-#endif 
+       OMAPLFB_CONSOLE_UNLOCK();
        if (res != 0 && res != -EINVAL)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_blank failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                return (OMAPLFB_ERROR_GENERIC);
        }
 #endif
-
        return (OMAPLFB_OK);
 }
 
 #ifdef CONFIG_HAS_EARLYSUSPEND
 
+/* Blank the screen */
 static void OMAPLFBBlankDisplay(OMAPLFB_DEVINFO *psDevInfo)
 {
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_lock();
-#else
-        acquire_console_sem();
-#endif
+       OMAPLFB_CONSOLE_LOCK();
        fb_blank(psDevInfo->psLINFBInfo, 1);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-        console_unlock();
-#else
-        release_console_sem();
-#endif
+       OMAPLFB_CONSOLE_UNLOCK();
 }
 
 static void OMAPLFBEarlySuspendHandler(struct early_suspend *h)
@@ -572,14 +954,15 @@ static void OMAPLFBEarlyResumeHandler(struct early_suspend *h)
        }
 }
 
-#endif 
+#endif /* CONFIG_HAS_EARLYSUSPEND */
 
+/* Set up Linux Framebuffer event notification */
 OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 {
        int                res;
        OMAPLFB_ERROR         eError;
 
-       
+       /* Set up Linux Framebuffer event notification */
        memset(&psDevInfo->sLINNotifBlock, 0, sizeof(psDevInfo->sLINNotifBlock));
 
        psDevInfo->sLINNotifBlock.notifier_call = OMAPLFBFrameBufferEvents;
@@ -590,7 +973,7 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        res = fb_register_client(&psDevInfo->sLINNotifBlock);
        if (res != 0)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_register_client failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
 
                return (OMAPLFB_ERROR_GENERIC);
@@ -599,7 +982,7 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        eError = OMAPLFBUnblankDisplay(psDevInfo);
        if (eError != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: UnblankDisplay failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, eError);
                return eError;
        }
@@ -607,13 +990,14 @@ OMAPLFB_ERROR OMAPLFBEnableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 #ifdef CONFIG_HAS_EARLYSUSPEND
        psDevInfo->sEarlySuspend.suspend = OMAPLFBEarlySuspendHandler;
        psDevInfo->sEarlySuspend.resume = OMAPLFBEarlyResumeHandler;
-       psDevInfo->sEarlySuspend.level = EARLY_SUSPEND_LEVEL_BLANK_SCREEN;
+       psDevInfo->sEarlySuspend.level = EARLY_SUSPEND_LEVEL_DISABLE_FB + 1;
        register_early_suspend(&psDevInfo->sEarlySuspend);
 #endif
 
        return (OMAPLFB_OK);
 }
 
+/* Disable Linux Framebuffer event notification */
 OMAPLFB_ERROR OMAPLFBDisableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
 {
        int res;
@@ -622,11 +1006,11 @@ OMAPLFB_ERROR OMAPLFBDisableLFBEventNotification(OMAPLFB_DEVINFO *psDevInfo)
        unregister_early_suspend(&psDevInfo->sEarlySuspend);
 #endif
 
-       
+       /* Unregister for Framebuffer events */
        res = fb_unregister_client(&psDevInfo->sLINNotifBlock);
        if (res != 0)
        {
-               printk(KERN_WARNING DRIVER_PREFIX
+               printk(KERN_ERR DRIVER_PREFIX
                        ": %s: Device %u: fb_unregister_client failed (%d)\n", __FUNCTION__, psDevInfo->uiFBDevID, res);
                return (OMAPLFB_ERROR_GENERIC);
        }
@@ -652,13 +1036,13 @@ static OMAPLFB_DEVINFO *OMAPLFBPVRDevIDToDevInfo(unsigned uiPVRDevID)
                }
        }
 
-       printk(KERN_WARNING DRIVER_PREFIX
+       printk(KERN_ERR DRIVER_PREFIX
                ": %s: PVR Device %u: Couldn't find device\n", __FUNCTION__, uiPVRDevID);
 
        return NULL;
 }
 
-int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg, struct drm_file unref__ *pFile)
+int PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Ioctl)(struct drm_device unref__ *dev, void *arg, struct drm_file unref__ *pFile)
 {
        uint32_t *puiArgs;
        uint32_t uiCmd;
@@ -737,7 +1121,7 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
                                                pszMode = "(Unknown Mode)";
                                                break;
                                }
-                               printk (KERN_WARNING DRIVER_PREFIX ": %s: PVR Device %u: Display %s\n",
+                               printk(KERN_WARNING DRIVER_PREFIX ": %s: PVR Device %u: Display %s\n",
                                __FUNCTION__, uiPVRDevID, pszMode);
                        }
 #endif
@@ -765,17 +1149,11 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
                        {
                                flush_workqueue(psDevInfo->psSwapChain->psWorkQueue);
                        }
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-                       console_lock();
-#else
-                       acquire_console_sem();
-#endif
+
+                       OMAPLFB_CONSOLE_LOCK();
                        ret = fb_blank(psDevInfo->psLINFBInfo, iFBMode);
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,38)
-                       console_unlock();
-#else
-                       release_console_sem();
-#endif
+                       OMAPLFB_CONSOLE_UNLOCK();
+
                        OMAPLFBCreateSwapChainUnLock(psDevInfo);
 
                        break;
@@ -791,8 +1169,9 @@ int PVR_DRM_MAKENAME(omaplfb, _Ioctl)(struct drm_device unref__ *dev, void *arg,
 }
 #endif
 
+/* Insert the driver into the kernel */
 #if defined(SUPPORT_DRI_DRM)
-int PVR_DRM_MAKENAME(omaplfb, _Init)(struct drm_device unref__ *dev)
+int PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Init)(struct drm_device unref__ *dev)
 #else
 static int __init OMAPLFB_Init(void)
 #endif
@@ -800,7 +1179,7 @@ static int __init OMAPLFB_Init(void)
 
        if(OMAPLFBInit() != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: OMAPLFBInit failed\n", __FUNCTION__);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: OMAPLFBInit failed\n", __FUNCTION__);
                return -ENODEV;
        }
 
@@ -808,19 +1187,26 @@ static int __init OMAPLFB_Init(void)
 
 }
 
+/* Remove the driver from the kernel */
 #if defined(SUPPORT_DRI_DRM)
-void PVR_DRM_MAKENAME(omaplfb, _Cleanup)(struct drm_device unref__ *dev)
+void PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Cleanup)(struct drm_device unref__ *dev)
 #else
 static void __exit OMAPLFB_Cleanup(void)
 #endif
 {    
        if(OMAPLFBDeInit() != OMAPLFB_OK)
        {
-               printk(KERN_WARNING DRIVER_PREFIX ": %s: OMAPLFBDeInit failed\n", __FUNCTION__);
+               printk(KERN_ERR DRIVER_PREFIX ": %s: OMAPLFBDeInit failed\n", __FUNCTION__);
        }
 }
 
 #if !defined(SUPPORT_DRI_DRM)
+/*
+ These macro calls define the initialisation and removal functions of the
+ driver.  Although they are prefixed `module_', they apply when compiling
+ statically as well; in both cases they define the function the kernel will
+ run to start/stop the driver.
+*/
 late_initcall(OMAPLFB_Init);
 module_exit(OMAPLFB_Cleanup);
 #endif
index 601f8f0..8c62f44 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 $(call must-be-defined,$(SUPPORT_DRI_DRM))
 
index caa349f..80733c5 100644 (file)
@@ -1,26 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 modules := linux_drm
 
diff --git a/services4/3rdparty/linux_drm/ati_pcigart.c b/services4/3rdparty/linux_drm/ati_pcigart.c
deleted file mode 100644 (file)
index 1c36492..0000000
+++ /dev/null
@@ -1,201 +0,0 @@
-/**
- * \file ati_pcigart.c
- * ATI PCI GART support
- *
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Wed Dec 13 21:52:19 2000 by gareth@valinux.com
- *
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-
-# define ATI_PCIGART_PAGE_SIZE         4096    /**< PCI GART page size */
-
-static int drm_ati_alloc_pcigart_table(struct drm_device *dev,
-                                      struct drm_ati_pcigart_info *gart_info)
-{
-       gart_info->table_handle = drm_pci_alloc(dev, gart_info->table_size,
-                                               PAGE_SIZE);
-       if (gart_info->table_handle == NULL)
-               return -ENOMEM;
-
-       return 0;
-}
-
-static void drm_ati_free_pcigart_table(struct drm_device *dev,
-                                      struct drm_ati_pcigart_info *gart_info)
-{
-       drm_pci_free(dev, gart_info->table_handle);
-       gart_info->table_handle = NULL;
-}
-
-int drm_ati_pcigart_cleanup(struct drm_device *dev, struct drm_ati_pcigart_info *gart_info)
-{
-       struct drm_sg_mem *entry = dev->sg;
-       unsigned long pages;
-       int i;
-       int max_pages;
-
-       /* we need to support large memory configurations */
-       if (!entry) {
-               DRM_ERROR("no scatter/gather memory!\n");
-               return 0;
-       }
-
-       if (gart_info->bus_addr) {
-
-               max_pages = (gart_info->table_size / sizeof(u32));
-               pages = (entry->pages <= max_pages)
-                 ? entry->pages : max_pages;
-
-               for (i = 0; i < pages; i++) {
-                       if (!entry->busaddr[i])
-                               break;
-                       pci_unmap_page(dev->pdev, entry->busaddr[i],
-                                        PAGE_SIZE, PCI_DMA_BIDIRECTIONAL);
-               }
-
-               if (gart_info->gart_table_location == DRM_ATI_GART_MAIN)
-                       gart_info->bus_addr = 0;
-       }
-
-       if (gart_info->gart_table_location == DRM_ATI_GART_MAIN &&
-           gart_info->table_handle) {
-               drm_ati_free_pcigart_table(dev, gart_info);
-       }
-
-       return 1;
-}
-EXPORT_SYMBOL(drm_ati_pcigart_cleanup);
-
-int drm_ati_pcigart_init(struct drm_device *dev, struct drm_ati_pcigart_info *gart_info)
-{
-       struct drm_local_map *map = &gart_info->mapping;
-       struct drm_sg_mem *entry = dev->sg;
-       void *address = NULL;
-       unsigned long pages;
-       u32 *pci_gart = NULL, page_base, gart_idx;
-       dma_addr_t bus_address = 0;
-       int i, j, ret = 0;
-       int max_ati_pages, max_real_pages;
-
-       if (!entry) {
-               DRM_ERROR("no scatter/gather memory!\n");
-               goto done;
-       }
-
-       if (gart_info->gart_table_location == DRM_ATI_GART_MAIN) {
-               DRM_DEBUG("PCI: no table in VRAM: using normal RAM\n");
-
-               if (pci_set_dma_mask(dev->pdev, gart_info->table_mask)) {
-                       DRM_ERROR("fail to set dma mask to 0x%Lx\n",
-                                 (unsigned long long)gart_info->table_mask);
-                       ret = 1;
-                       goto done;
-               }
-
-               ret = drm_ati_alloc_pcigart_table(dev, gart_info);
-               if (ret) {
-                       DRM_ERROR("cannot allocate PCI GART page!\n");
-                       goto done;
-               }
-
-               pci_gart = gart_info->table_handle->vaddr;
-               address = gart_info->table_handle->vaddr;
-               bus_address = gart_info->table_handle->busaddr;
-       } else {
-               address = gart_info->addr;
-               bus_address = gart_info->bus_addr;
-               DRM_DEBUG("PCI: Gart Table: VRAM %08LX mapped at %08lX\n",
-                         (unsigned long long)bus_address,
-                         (unsigned long)address);
-       }
-
-
-       max_ati_pages = (gart_info->table_size / sizeof(u32));
-       max_real_pages = max_ati_pages / (PAGE_SIZE / ATI_PCIGART_PAGE_SIZE);
-       pages = (entry->pages <= max_real_pages)
-           ? entry->pages : max_real_pages;
-
-       if (gart_info->gart_table_location == DRM_ATI_GART_MAIN) {
-               memset(pci_gart, 0, max_ati_pages * sizeof(u32));
-       } else {
-               memset_io((void __iomem *)map->handle, 0, max_ati_pages * sizeof(u32));
-       }
-
-       gart_idx = 0;
-       for (i = 0; i < pages; i++) {
-               /* we need to support large memory configurations */
-               entry->busaddr[i] = pci_map_page(dev->pdev, entry->pagelist[i],
-                                                0, PAGE_SIZE, PCI_DMA_BIDIRECTIONAL);
-               if (pci_dma_mapping_error(dev->pdev, entry->busaddr[i])) {
-                       DRM_ERROR("unable to map PCIGART pages!\n");
-                       drm_ati_pcigart_cleanup(dev, gart_info);
-                       address = NULL;
-                       bus_address = 0;
-                       goto done;
-               }
-               page_base = (u32) entry->busaddr[i];
-
-               for (j = 0; j < (PAGE_SIZE / ATI_PCIGART_PAGE_SIZE); j++) {
-                       u32 val;
-
-                       switch(gart_info->gart_reg_if) {
-                       case DRM_ATI_GART_IGP:
-                               val = page_base | 0xc;
-                               break;
-                       case DRM_ATI_GART_PCIE:
-                               val = (page_base >> 8) | 0xc;
-                               break;
-                       default:
-                       case DRM_ATI_GART_PCI:
-                               val = page_base;
-                               break;
-                       }
-                       if (gart_info->gart_table_location ==
-                           DRM_ATI_GART_MAIN)
-                               pci_gart[gart_idx] = cpu_to_le32(val);
-                       else
-                               DRM_WRITE32(map, gart_idx * sizeof(u32), val);
-                       gart_idx++;
-                       page_base += ATI_PCIGART_PAGE_SIZE;
-               }
-       }
-       ret = 1;
-
-#if defined(__i386__) || defined(__x86_64__)
-       wbinvd();
-#else
-       mb();
-#endif
-
-      done:
-       gart_info->addr = address;
-       gart_info->bus_addr = bus_address;
-       return ret;
-}
-EXPORT_SYMBOL(drm_ati_pcigart_init);
diff --git a/services4/3rdparty/linux_drm/drm_agpsupport.c b/services4/3rdparty/linux_drm/drm_agpsupport.c
deleted file mode 100644 (file)
index 252fdb9..0000000
+++ /dev/null
@@ -1,475 +0,0 @@
-/**
- * \file drm_agpsupport.c
- * DRM support for AGP/GART backend
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-#include <linux/module.h>
-#include <linux/slab.h>
-
-#if __OS_HAS_AGP
-
-#include <asm/agp.h>
-
-/**
- * Get AGP information.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a (output) drm_agp_info structure.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device has been initialized and acquired and fills in the
- * drm_agp_info structure with the information in drm_agp_head::agp_info.
- */
-int drm_agp_info(struct drm_device *dev, struct drm_agp_info *info)
-{
-       DRM_AGP_KERN *kern;
-
-       if (!dev->agp || !dev->agp->acquired)
-               return -EINVAL;
-
-       kern = &dev->agp->agp_info;
-       info->agp_version_major = kern->version.major;
-       info->agp_version_minor = kern->version.minor;
-       info->mode = kern->mode;
-       info->aperture_base = kern->aper_base;
-       info->aperture_size = kern->aper_size * 1024 * 1024;
-       info->memory_allowed = kern->max_memory << PAGE_SHIFT;
-       info->memory_used = kern->current_memory << PAGE_SHIFT;
-       info->id_vendor = kern->device->vendor;
-       info->id_device = kern->device->device;
-
-       return 0;
-}
-
-EXPORT_SYMBOL(drm_agp_info);
-
-int drm_agp_info_ioctl(struct drm_device *dev, void *data,
-                      struct drm_file *file_priv)
-{
-       struct drm_agp_info *info = data;
-       int err;
-
-       err = drm_agp_info(dev, info);
-       if (err)
-               return err;
-
-       return 0;
-}
-
-/**
- * Acquire the AGP device.
- *
- * \param dev DRM device that is to acquire AGP.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device hasn't been acquired before and calls
- * \c agp_backend_acquire.
- */
-int drm_agp_acquire(struct drm_device * dev)
-{
-       if (!dev->agp)
-               return -ENODEV;
-       if (dev->agp->acquired)
-               return -EBUSY;
-       if (!(dev->agp->bridge = agp_backend_acquire(dev->pdev)))
-               return -ENODEV;
-       dev->agp->acquired = 1;
-       return 0;
-}
-
-EXPORT_SYMBOL(drm_agp_acquire);
-
-/**
- * Acquire the AGP device (ioctl).
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device hasn't been acquired before and calls
- * \c agp_backend_acquire.
- */
-int drm_agp_acquire_ioctl(struct drm_device *dev, void *data,
-                         struct drm_file *file_priv)
-{
-       return drm_agp_acquire((struct drm_device *) file_priv->minor->dev);
-}
-
-/**
- * Release the AGP device.
- *
- * \param dev DRM device that is to release AGP.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device has been acquired and calls \c agp_backend_release.
- */
-int drm_agp_release(struct drm_device * dev)
-{
-       if (!dev->agp || !dev->agp->acquired)
-               return -EINVAL;
-       agp_backend_release(dev->agp->bridge);
-       dev->agp->acquired = 0;
-       return 0;
-}
-EXPORT_SYMBOL(drm_agp_release);
-
-int drm_agp_release_ioctl(struct drm_device *dev, void *data,
-                         struct drm_file *file_priv)
-{
-       return drm_agp_release(dev);
-}
-
-/**
- * Enable the AGP bus.
- *
- * \param dev DRM device that has previously acquired AGP.
- * \param mode Requested AGP mode.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device has been acquired but not enabled, and calls
- * \c agp_enable.
- */
-int drm_agp_enable(struct drm_device * dev, struct drm_agp_mode mode)
-{
-       if (!dev->agp || !dev->agp->acquired)
-               return -EINVAL;
-
-       dev->agp->mode = mode.mode;
-       agp_enable(dev->agp->bridge, mode.mode);
-       dev->agp->enabled = 1;
-       return 0;
-}
-
-EXPORT_SYMBOL(drm_agp_enable);
-
-int drm_agp_enable_ioctl(struct drm_device *dev, void *data,
-                        struct drm_file *file_priv)
-{
-       struct drm_agp_mode *mode = data;
-
-       return drm_agp_enable(dev, *mode);
-}
-
-/**
- * Allocate AGP memory.
- *
- * \param inode device inode.
- * \param file_priv file private pointer.
- * \param cmd command.
- * \param arg pointer to a drm_agp_buffer structure.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device is present and has been acquired, allocates the
- * memory via agp_allocate_memory() and creates a drm_agp_mem entry for it.
- */
-int drm_agp_alloc(struct drm_device *dev, struct drm_agp_buffer *request)
-{
-       struct drm_agp_mem *entry;
-       DRM_AGP_MEM *memory;
-       unsigned long pages;
-       u32 type;
-
-       if (!dev->agp || !dev->agp->acquired)
-               return -EINVAL;
-       if (!(entry = kmalloc(sizeof(*entry), GFP_KERNEL)))
-               return -ENOMEM;
-
-       memset(entry, 0, sizeof(*entry));
-
-       pages = (request->size + PAGE_SIZE - 1) / PAGE_SIZE;
-       type = (u32) request->type;
-       if (!(memory = agp_allocate_memory(dev->agp->bridge, pages, type))) {
-               kfree(entry);
-               return -ENOMEM;
-       }
-
-       entry->handle = (unsigned long)memory->key + 1;
-       entry->memory = memory;
-       entry->bound = 0;
-       entry->pages = pages;
-       list_add(&entry->head, &dev->agp->memory);
-
-       request->handle = entry->handle;
-       request->physical = memory->physical;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_agp_alloc);
-
-
-int drm_agp_alloc_ioctl(struct drm_device *dev, void *data,
-                       struct drm_file *file_priv)
-{
-       struct drm_agp_buffer *request = data;
-
-       return drm_agp_alloc(dev, request);
-}
-
-/**
- * Search for the AGP memory entry associated with a handle.
- *
- * \param dev DRM device structure.
- * \param handle AGP memory handle.
- * \return pointer to the drm_agp_mem structure associated with \p handle.
- *
- * Walks through drm_agp_head::memory until finding a matching handle.
- */
-static struct drm_agp_mem *drm_agp_lookup_entry(struct drm_device * dev,
-                                          unsigned long handle)
-{
-       struct drm_agp_mem *entry;
-
-       list_for_each_entry(entry, &dev->agp->memory, head) {
-               if (entry->handle == handle)
-                       return entry;
-       }
-       return NULL;
-}
-
-/**
- * Unbind AGP memory from the GATT (ioctl).
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a drm_agp_binding structure.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device is present and acquired, looks-up the AGP memory
- * entry and passes it to the unbind_agp() function.
- */
-int drm_agp_unbind(struct drm_device *dev, struct drm_agp_binding *request)
-{
-       struct drm_agp_mem *entry;
-       int ret;
-
-       if (!dev->agp || !dev->agp->acquired)
-               return -EINVAL;
-       if (!(entry = drm_agp_lookup_entry(dev, request->handle)))
-               return -EINVAL;
-       if (!entry->bound)
-               return -EINVAL;
-       ret = drm_unbind_agp(entry->memory);
-       if (ret == 0)
-               entry->bound = 0;
-       return ret;
-}
-EXPORT_SYMBOL(drm_agp_unbind);
-
-
-int drm_agp_unbind_ioctl(struct drm_device *dev, void *data,
-                        struct drm_file *file_priv)
-{
-       struct drm_agp_binding *request = data;
-
-       return drm_agp_unbind(dev, request);
-}
-
-/**
- * Bind AGP memory into the GATT (ioctl)
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a drm_agp_binding structure.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device is present and has been acquired and that no memory
- * is currently bound into the GATT. Looks-up the AGP memory entry and passes
- * it to bind_agp() function.
- */
-int drm_agp_bind(struct drm_device *dev, struct drm_agp_binding *request)
-{
-       struct drm_agp_mem *entry;
-       int retcode;
-       int page;
-
-       if (!dev->agp || !dev->agp->acquired)
-               return -EINVAL;
-       if (!(entry = drm_agp_lookup_entry(dev, request->handle)))
-               return -EINVAL;
-       if (entry->bound)
-               return -EINVAL;
-       page = (request->offset + PAGE_SIZE - 1) / PAGE_SIZE;
-       if ((retcode = drm_bind_agp(entry->memory, page)))
-               return retcode;
-       entry->bound = dev->agp->base + (page << PAGE_SHIFT);
-       DRM_DEBUG("base = 0x%lx entry->bound = 0x%lx\n",
-                 dev->agp->base, entry->bound);
-       return 0;
-}
-EXPORT_SYMBOL(drm_agp_bind);
-
-
-int drm_agp_bind_ioctl(struct drm_device *dev, void *data,
-                      struct drm_file *file_priv)
-{
-       struct drm_agp_binding *request = data;
-
-       return drm_agp_bind(dev, request);
-}
-
-/**
- * Free AGP memory (ioctl).
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a drm_agp_buffer structure.
- * \return zero on success or a negative number on failure.
- *
- * Verifies the AGP device is present and has been acquired and looks up the
- * AGP memory entry. If the memory it's currently bound, unbind it via
- * unbind_agp(). Frees it via free_agp() as well as the entry itself
- * and unlinks from the doubly linked list it's inserted in.
- */
-int drm_agp_free(struct drm_device *dev, struct drm_agp_buffer *request)
-{
-       struct drm_agp_mem *entry;
-
-       if (!dev->agp || !dev->agp->acquired)
-               return -EINVAL;
-       if (!(entry = drm_agp_lookup_entry(dev, request->handle)))
-               return -EINVAL;
-       if (entry->bound)
-               drm_unbind_agp(entry->memory);
-
-       list_del(&entry->head);
-
-       drm_free_agp(entry->memory, entry->pages);
-       kfree(entry);
-       return 0;
-}
-EXPORT_SYMBOL(drm_agp_free);
-
-
-
-int drm_agp_free_ioctl(struct drm_device *dev, void *data,
-                      struct drm_file *file_priv)
-{
-       struct drm_agp_buffer *request = data;
-
-       return drm_agp_free(dev, request);
-}
-
-/**
- * Initialize the AGP resources.
- *
- * \return pointer to a drm_agp_head structure.
- *
- * Gets the drm_agp_t structure which is made available by the agpgart module
- * via the inter_module_* functions. Creates and initializes a drm_agp_head
- * structure.
- */
-struct drm_agp_head *drm_agp_init(struct drm_device *dev)
-{
-       struct drm_agp_head *head = NULL;
-
-       if (!(head = kmalloc(sizeof(*head), GFP_KERNEL)))
-               return NULL;
-       memset((void *)head, 0, sizeof(*head));
-       head->bridge = agp_find_bridge(dev->pdev);
-       if (!head->bridge) {
-               if (!(head->bridge = agp_backend_acquire(dev->pdev))) {
-                       kfree(head);
-                       return NULL;
-               }
-               agp_copy_info(head->bridge, &head->agp_info);
-               agp_backend_release(head->bridge);
-       } else {
-               agp_copy_info(head->bridge, &head->agp_info);
-       }
-       if (head->agp_info.chipset == NOT_SUPPORTED) {
-               kfree(head);
-               return NULL;
-       }
-       INIT_LIST_HEAD(&head->memory);
-       head->cant_use_aperture = head->agp_info.cant_use_aperture;
-       head->page_mask = head->agp_info.page_mask;
-       head->base = head->agp_info.aper_base;
-       return head;
-}
-
-/**
- * Binds a collection of pages into AGP memory at the given offset, returning
- * the AGP memory structure containing them.
- *
- * No reference is held on the pages during this time -- it is up to the
- * caller to handle that.
- */
-DRM_AGP_MEM *
-drm_agp_bind_pages(struct drm_device *dev,
-                  struct page **pages,
-                  unsigned long num_pages,
-                  uint32_t gtt_offset,
-                  u32 type)
-{
-       DRM_AGP_MEM *mem;
-       int ret, i;
-
-       DRM_DEBUG("\n");
-
-       mem = agp_allocate_memory(dev->agp->bridge, num_pages,
-                                     type);
-       if (mem == NULL) {
-               DRM_ERROR("Failed to allocate memory for %ld pages\n",
-                         num_pages);
-               return NULL;
-       }
-
-       for (i = 0; i < num_pages; i++)
-               mem->pages[i] = pages[i];
-       mem->page_count = num_pages;
-
-       mem->is_flushed = true;
-       ret = agp_bind_memory(mem, gtt_offset / PAGE_SIZE);
-       if (ret != 0) {
-               DRM_ERROR("Failed to bind AGP memory: %d\n", ret);
-               agp_free_memory(mem);
-               return NULL;
-       }
-
-       return mem;
-}
-EXPORT_SYMBOL(drm_agp_bind_pages);
-
-void drm_agp_chipset_flush(struct drm_device *dev)
-{
-       agp_flush_chipset(dev->agp->bridge);
-}
-EXPORT_SYMBOL(drm_agp_chipset_flush);
-
-#endif /* __OS_HAS_AGP */
diff --git a/services4/3rdparty/linux_drm/drm_auth.c b/services4/3rdparty/linux_drm/drm_auth.c
deleted file mode 100644 (file)
index 3f46772..0000000
+++ /dev/null
@@ -1,190 +0,0 @@
-/**
- * \file drm_auth.c
- * IOCTLs for authentication
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Tue Feb  2 08:37:54 1999 by faith@valinux.com
- *
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-
-/**
- * Find the file with the given magic number.
- *
- * \param dev DRM device.
- * \param magic magic number.
- *
- * Searches in drm_device::magiclist within all files with the same hash key
- * the one with matching magic number, while holding the drm_device::struct_mutex
- * lock.
- */
-static struct drm_file *drm_find_file(struct drm_master *master, drm_magic_t magic)
-{
-       struct drm_file *retval = NULL;
-       struct drm_magic_entry *pt;
-       struct drm_hash_item *hash;
-       struct drm_device *dev = master->minor->dev;
-
-       mutex_lock(&dev->struct_mutex);
-       if (!drm_ht_find_item(&master->magiclist, (unsigned long)magic, &hash)) {
-               pt = drm_hash_entry(hash, struct drm_magic_entry, hash_item);
-               retval = pt->priv;
-       }
-       mutex_unlock(&dev->struct_mutex);
-       return retval;
-}
-
-/**
- * Adds a magic number.
- *
- * \param dev DRM device.
- * \param priv file private data.
- * \param magic magic number.
- *
- * Creates a drm_magic_entry structure and appends to the linked list
- * associated the magic number hash key in drm_device::magiclist, while holding
- * the drm_device::struct_mutex lock.
- */
-static int drm_add_magic(struct drm_master *master, struct drm_file *priv,
-                        drm_magic_t magic)
-{
-       struct drm_magic_entry *entry;
-       struct drm_device *dev = master->minor->dev;
-       DRM_DEBUG("%d\n", magic);
-
-       entry = kzalloc(sizeof(*entry), GFP_KERNEL);
-       if (!entry)
-               return -ENOMEM;
-       entry->priv = priv;
-       entry->hash_item.key = (unsigned long)magic;
-       mutex_lock(&dev->struct_mutex);
-       drm_ht_insert_item(&master->magiclist, &entry->hash_item);
-       list_add_tail(&entry->head, &master->magicfree);
-       mutex_unlock(&dev->struct_mutex);
-
-       return 0;
-}
-
-/**
- * Remove a magic number.
- *
- * \param dev DRM device.
- * \param magic magic number.
- *
- * Searches and unlinks the entry in drm_device::magiclist with the magic
- * number hash key, while holding the drm_device::struct_mutex lock.
- */
-static int drm_remove_magic(struct drm_master *master, drm_magic_t magic)
-{
-       struct drm_magic_entry *pt;
-       struct drm_hash_item *hash;
-       struct drm_device *dev = master->minor->dev;
-
-       DRM_DEBUG("%d\n", magic);
-
-       mutex_lock(&dev->struct_mutex);
-       if (drm_ht_find_item(&master->magiclist, (unsigned long)magic, &hash)) {
-               mutex_unlock(&dev->struct_mutex);
-               return -EINVAL;
-       }
-       pt = drm_hash_entry(hash, struct drm_magic_entry, hash_item);
-       drm_ht_remove_item(&master->magiclist, hash);
-       list_del(&pt->head);
-       mutex_unlock(&dev->struct_mutex);
-
-       kfree(pt);
-
-       return 0;
-}
-
-/**
- * Get a unique magic number (ioctl).
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a resulting drm_auth structure.
- * \return zero on success, or a negative number on failure.
- *
- * If there is a magic number in drm_file::magic then use it, otherwise
- * searches an unique non-zero magic number and add it associating it with \p
- * file_priv.
- */
-int drm_getmagic(struct drm_device *dev, void *data, struct drm_file *file_priv)
-{
-       static drm_magic_t sequence = 0;
-       static DEFINE_SPINLOCK(lock);
-       struct drm_auth *auth = data;
-
-       /* Find unique magic */
-       if (file_priv->magic) {
-               auth->magic = file_priv->magic;
-       } else {
-               do {
-                       spin_lock(&lock);
-                       if (!sequence)
-                               ++sequence;     /* reserve 0 */
-                       auth->magic = sequence++;
-                       spin_unlock(&lock);
-               } while (drm_find_file(file_priv->master, auth->magic));
-               file_priv->magic = auth->magic;
-               drm_add_magic(file_priv->master, file_priv, auth->magic);
-       }
-
-       DRM_DEBUG("%u\n", auth->magic);
-
-       return 0;
-}
-
-/**
- * Authenticate with a magic.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a drm_auth structure.
- * \return zero if authentication successed, or a negative number otherwise.
- *
- * Checks if \p file_priv is associated with the magic number passed in \arg.
- */
-int drm_authmagic(struct drm_device *dev, void *data,
-                 struct drm_file *file_priv)
-{
-       struct drm_auth *auth = data;
-       struct drm_file *file;
-
-       DRM_DEBUG("%u\n", auth->magic);
-       if ((file = drm_find_file(file_priv->master, auth->magic))) {
-               file->authenticated = 1;
-               drm_remove_magic(file_priv->master, auth->magic);
-               return 0;
-       }
-       return -EINVAL;
-}
diff --git a/services4/3rdparty/linux_drm/drm_buffer.c b/services4/3rdparty/linux_drm/drm_buffer.c
deleted file mode 100644 (file)
index 529a0db..0000000
+++ /dev/null
@@ -1,184 +0,0 @@
-/**************************************************************************
- *
- * Copyright 2010 Pauli Nieminen.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sub license, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice (including the
- * next paragraph) shall be included in all copies or substantial portions
- * of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
- * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
- * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
- * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
- * USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- *
- **************************************************************************/
-/*
- * Multipart buffer for coping data which is larger than the page size.
- *
- * Authors:
- * Pauli Nieminen <suokkos-at-gmail-dot-com>
- */
-
-#include "drm_buffer.h"
-
-/**
- * Allocate the drm buffer object.
- *
- *   buf: Pointer to a pointer where the object is stored.
- *   size: The number of bytes to allocate.
- */
-int drm_buffer_alloc(struct drm_buffer **buf, int size)
-{
-       int nr_pages = size / PAGE_SIZE + 1;
-       int idx;
-
-       /* Allocating pointer table to end of structure makes drm_buffer
-        * variable sized */
-       *buf = kzalloc(sizeof(struct drm_buffer) + nr_pages*sizeof(char *),
-                       GFP_KERNEL);
-
-       if (*buf == NULL) {
-               DRM_ERROR("Failed to allocate drm buffer object to hold"
-                               " %d bytes in %d pages.\n",
-                               size, nr_pages);
-               return -ENOMEM;
-       }
-
-       (*buf)->size = size;
-
-       for (idx = 0; idx < nr_pages; ++idx) {
-
-               (*buf)->data[idx] =
-                       kmalloc(min(PAGE_SIZE, size - idx * PAGE_SIZE),
-                               GFP_KERNEL);
-
-
-               if ((*buf)->data[idx] == NULL) {
-                       DRM_ERROR("Failed to allocate %dth page for drm"
-                                       " buffer with %d bytes and %d pages.\n",
-                                       idx + 1, size, nr_pages);
-                       goto error_out;
-               }
-
-       }
-
-       return 0;
-
-error_out:
-
-       /* Only last element can be null pointer so check for it first. */
-       if ((*buf)->data[idx])
-               kfree((*buf)->data[idx]);
-
-       for (--idx; idx >= 0; --idx)
-               kfree((*buf)->data[idx]);
-
-       kfree(*buf);
-       return -ENOMEM;
-}
-EXPORT_SYMBOL(drm_buffer_alloc);
-
-/**
- * Copy the user data to the begin of the buffer and reset the processing
- * iterator.
- *
- *   user_data: A pointer the data that is copied to the buffer.
- *   size: The Number of bytes to copy.
- */
-int drm_buffer_copy_from_user(struct drm_buffer *buf,
-                             void __user *user_data, int size)
-{
-       int nr_pages = size / PAGE_SIZE + 1;
-       int idx;
-
-       if (size > buf->size) {
-               DRM_ERROR("Requesting to copy %d bytes to a drm buffer with"
-                               " %d bytes space\n",
-                               size, buf->size);
-               return -EFAULT;
-       }
-
-       for (idx = 0; idx < nr_pages; ++idx) {
-
-               if (DRM_COPY_FROM_USER(buf->data[idx],
-                       user_data + idx * PAGE_SIZE,
-                       min(PAGE_SIZE, size - idx * PAGE_SIZE))) {
-                       DRM_ERROR("Failed to copy user data (%p) to drm buffer"
-                                       " (%p) %dth page.\n",
-                                       user_data, buf, idx);
-                       return -EFAULT;
-
-               }
-       }
-       buf->iterator = 0;
-       return 0;
-}
-EXPORT_SYMBOL(drm_buffer_copy_from_user);
-
-/**
- * Free the drm buffer object
- */
-void drm_buffer_free(struct drm_buffer *buf)
-{
-
-       if (buf != NULL) {
-
-               int nr_pages = buf->size / PAGE_SIZE + 1;
-               int idx;
-               for (idx = 0; idx < nr_pages; ++idx)
-                       kfree(buf->data[idx]);
-
-               kfree(buf);
-       }
-}
-EXPORT_SYMBOL(drm_buffer_free);
-
-/**
- * Read an object from buffer that may be split to multiple parts. If object
- * is not split function just returns the pointer to object in buffer. But in
- * case of split object data is copied to given stack object that is suplied
- * by caller.
- *
- * The processing location of the buffer is also advanced to the next byte
- * after the object.
- *
- *   objsize: The size of the objet in bytes.
- *   stack_obj: A pointer to a memory location where object can be copied.
- */
-void *drm_buffer_read_object(struct drm_buffer *buf,
-               int objsize, void *stack_obj)
-{
-       int idx = drm_buffer_index(buf);
-       int page = drm_buffer_page(buf);
-       void *obj = NULL;
-
-       if (idx + objsize <= PAGE_SIZE) {
-               obj = &buf->data[page][idx];
-       } else {
-               /* The object is split which forces copy to temporary object.*/
-               int beginsz = PAGE_SIZE - idx;
-               memcpy(stack_obj, &buf->data[page][idx], beginsz);
-
-               memcpy(stack_obj + beginsz, &buf->data[page + 1][0],
-                               objsize - beginsz);
-
-               obj = stack_obj;
-       }
-
-       drm_buffer_advance(buf, objsize);
-       return obj;
-}
-EXPORT_SYMBOL(drm_buffer_read_object);
diff --git a/services4/3rdparty/linux_drm/drm_bufs.c b/services4/3rdparty/linux_drm/drm_bufs.c
deleted file mode 100644 (file)
index 3e257a5..0000000
+++ /dev/null
@@ -1,1628 +0,0 @@
-/**
- * \file drm_bufs.c
- * Generic buffer template
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Thu Nov 23 03:10:50 2000 by gareth@valinux.com
- *
- * Copyright 1999, 2000 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/vmalloc.h>
-#include <linux/slab.h>
-#include <linux/log2.h>
-#include <asm/shmparam.h>
-#include "drmP.h"
-
-static struct drm_map_list *drm_find_matching_map(struct drm_device *dev,
-                                                 struct drm_local_map *map)
-{
-       struct drm_map_list *entry;
-       list_for_each_entry(entry, &dev->maplist, head) {
-               /*
-                * Because the kernel-userspace ABI is fixed at a 32-bit offset
-                * while PCI resources may live above that, we ignore the map
-                * offset for maps of type _DRM_FRAMEBUFFER or _DRM_REGISTERS.
-                * It is assumed that each driver will have only one resource of
-                * each type.
-                */
-               if (!entry->map ||
-                   map->type != entry->map->type ||
-                   entry->master != dev->primary->master)
-                       continue;
-               switch (map->type) {
-               case _DRM_SHM:
-                       if (map->flags != _DRM_CONTAINS_LOCK)
-                               break;
-               case _DRM_REGISTERS:
-               case _DRM_FRAME_BUFFER:
-                       return entry;
-               default: /* Make gcc happy */
-                       ;
-               }
-               if (entry->map->offset == map->offset)
-                       return entry;
-       }
-
-       return NULL;
-}
-
-static int drm_map_handle(struct drm_device *dev, struct drm_hash_item *hash,
-                         unsigned long user_token, int hashed_handle, int shm)
-{
-       int use_hashed_handle, shift;
-       unsigned long add;
-
-#if (BITS_PER_LONG == 64)
-       use_hashed_handle = ((user_token & 0xFFFFFFFF00000000UL) || hashed_handle);
-#elif (BITS_PER_LONG == 32)
-       use_hashed_handle = hashed_handle;
-#else
-#error Unsupported long size. Neither 64 nor 32 bits.
-#endif
-
-       if (!use_hashed_handle) {
-               int ret;
-               hash->key = user_token >> PAGE_SHIFT;
-               ret = drm_ht_insert_item(&dev->map_hash, hash);
-               if (ret != -EINVAL)
-                       return ret;
-       }
-
-       shift = 0;
-       add = DRM_MAP_HASH_OFFSET >> PAGE_SHIFT;
-       if (shm && (SHMLBA > PAGE_SIZE)) {
-               int bits = ilog2(SHMLBA >> PAGE_SHIFT) + 1;
-
-               /* For shared memory, we have to preserve the SHMLBA
-                * bits of the eventual vma->vm_pgoff value during
-                * mmap().  Otherwise we run into cache aliasing problems
-                * on some platforms.  On these platforms, the pgoff of
-                * a mmap() request is used to pick a suitable virtual
-                * address for the mmap() region such that it will not
-                * cause cache aliasing problems.
-                *
-                * Therefore, make sure the SHMLBA relevant bits of the
-                * hash value we use are equal to those in the original
-                * kernel virtual address.
-                */
-               shift = bits;
-               add |= ((user_token >> PAGE_SHIFT) & ((1UL << bits) - 1UL));
-       }
-
-       return drm_ht_just_insert_please(&dev->map_hash, hash,
-                                        user_token, 32 - PAGE_SHIFT - 3,
-                                        shift, add);
-}
-
-/**
- * Core function to create a range of memory available for mapping by a
- * non-root process.
- *
- * Adjusts the memory offset to its absolute value according to the mapping
- * type.  Adds the map to the map list drm_device::maplist. Adds MTRR's where
- * applicable and if supported by the kernel.
- */
-static int drm_addmap_core(struct drm_device * dev, resource_size_t offset,
-                          unsigned int size, enum drm_map_type type,
-                          enum drm_map_flags flags,
-                          struct drm_map_list ** maplist)
-{
-       struct drm_local_map *map;
-       struct drm_map_list *list;
-       drm_dma_handle_t *dmah;
-       unsigned long user_token;
-       int ret;
-
-       map = kmalloc(sizeof(*map), GFP_KERNEL);
-       if (!map)
-               return -ENOMEM;
-
-       map->offset = offset;
-       map->size = size;
-       map->flags = flags;
-       map->type = type;
-
-       /* Only allow shared memory to be removable since we only keep enough
-        * book keeping information about shared memory to allow for removal
-        * when processes fork.
-        */
-       if ((map->flags & _DRM_REMOVABLE) && map->type != _DRM_SHM) {
-               kfree(map);
-               return -EINVAL;
-       }
-       DRM_DEBUG("offset = 0x%08llx, size = 0x%08lx, type = %d\n",
-                 (unsigned long long)map->offset, map->size, map->type);
-
-       /* page-align _DRM_SHM maps. They are allocated here so there is no security
-        * hole created by that and it works around various broken drivers that use
-        * a non-aligned quantity to map the SAREA. --BenH
-        */
-       if (map->type == _DRM_SHM)
-               map->size = PAGE_ALIGN(map->size);
-
-       if ((map->offset & (~(resource_size_t)PAGE_MASK)) || (map->size & (~PAGE_MASK))) {
-               kfree(map);
-               return -EINVAL;
-       }
-       map->mtrr = -1;
-       map->handle = NULL;
-
-       switch (map->type) {
-       case _DRM_REGISTERS:
-       case _DRM_FRAME_BUFFER:
-#if !defined(__sparc__) && !defined(__alpha__) && !defined(__ia64__) && !defined(__powerpc64__) && !defined(__x86_64__) && !defined(__arm__)
-               if (map->offset + (map->size-1) < map->offset ||
-                   map->offset < virt_to_phys(high_memory)) {
-                       kfree(map);
-                       return -EINVAL;
-               }
-#endif
-#ifdef __alpha__
-               map->offset += dev->hose->mem_space->start;
-#endif
-               /* Some drivers preinitialize some maps, without the X Server
-                * needing to be aware of it.  Therefore, we just return success
-                * when the server tries to create a duplicate map.
-                */
-               list = drm_find_matching_map(dev, map);
-               if (list != NULL) {
-                       if (list->map->size != map->size) {
-                               DRM_DEBUG("Matching maps of type %d with "
-                                         "mismatched sizes, (%ld vs %ld)\n",
-                                         map->type, map->size,
-                                         list->map->size);
-                               list->map->size = map->size;
-                       }
-
-                       kfree(map);
-                       *maplist = list;
-                       return 0;
-               }
-
-               if (drm_core_has_MTRR(dev)) {
-                       if (map->type == _DRM_FRAME_BUFFER ||
-                           (map->flags & _DRM_WRITE_COMBINING)) {
-                               map->mtrr = mtrr_add(map->offset, map->size,
-                                                    MTRR_TYPE_WRCOMB, 1);
-                       }
-               }
-               if (map->type == _DRM_REGISTERS) {
-                       map->handle = ioremap(map->offset, map->size);
-                       if (!map->handle) {
-                               kfree(map);
-                               return -ENOMEM;
-                       }
-               }
-
-               break;
-       case _DRM_SHM:
-               list = drm_find_matching_map(dev, map);
-               if (list != NULL) {
-                       if(list->map->size != map->size) {
-                               DRM_DEBUG("Matching maps of type %d with "
-                                         "mismatched sizes, (%ld vs %ld)\n",
-                                         map->type, map->size, list->map->size);
-                               list->map->size = map->size;
-                       }
-
-                       kfree(map);
-                       *maplist = list;
-                       return 0;
-               }
-               map->handle = vmalloc_user(map->size);
-               DRM_DEBUG("%lu %d %p\n",
-                         map->size, drm_order(map->size), map->handle);
-               if (!map->handle) {
-                       kfree(map);
-                       return -ENOMEM;
-               }
-               map->offset = (unsigned long)map->handle;
-               if (map->flags & _DRM_CONTAINS_LOCK) {
-                       /* Prevent a 2nd X Server from creating a 2nd lock */
-                       if (dev->primary->master->lock.hw_lock != NULL) {
-                               vfree(map->handle);
-                               kfree(map);
-                               return -EBUSY;
-                       }
-                       dev->sigdata.lock = dev->primary->master->lock.hw_lock = map->handle;   /* Pointer to lock */
-               }
-               break;
-       case _DRM_AGP: {
-               struct drm_agp_mem *entry;
-               int valid = 0;
-
-               if (!drm_core_has_AGP(dev)) {
-                       kfree(map);
-                       return -EINVAL;
-               }
-#ifdef __alpha__
-               map->offset += dev->hose->mem_space->start;
-#endif
-               /* In some cases (i810 driver), user space may have already
-                * added the AGP base itself, because dev->agp->base previously
-                * only got set during AGP enable.  So, only add the base
-                * address if the map's offset isn't already within the
-                * aperture.
-                */
-               if (map->offset < dev->agp->base ||
-                   map->offset > dev->agp->base +
-                   dev->agp->agp_info.aper_size * 1024 * 1024 - 1) {
-                       map->offset += dev->agp->base;
-               }
-               map->mtrr = dev->agp->agp_mtrr; /* for getmap */
-
-               /* This assumes the DRM is in total control of AGP space.
-                * It's not always the case as AGP can be in the control
-                * of user space (i.e. i810 driver). So this loop will get
-                * skipped and we double check that dev->agp->memory is
-                * actually set as well as being invalid before EPERM'ing
-                */
-               list_for_each_entry(entry, &dev->agp->memory, head) {
-                       if ((map->offset >= entry->bound) &&
-                           (map->offset + map->size <= entry->bound + entry->pages * PAGE_SIZE)) {
-                               valid = 1;
-                               break;
-                       }
-               }
-               if (!list_empty(&dev->agp->memory) && !valid) {
-                       kfree(map);
-                       return -EPERM;
-               }
-               DRM_DEBUG("AGP offset = 0x%08llx, size = 0x%08lx\n",
-                         (unsigned long long)map->offset, map->size);
-
-               break;
-       }
-       case _DRM_GEM:
-               DRM_ERROR("tried to addmap GEM object\n");
-               break;
-       case _DRM_SCATTER_GATHER:
-               if (!dev->sg) {
-                       kfree(map);
-                       return -EINVAL;
-               }
-               map->offset += (unsigned long)dev->sg->virtual;
-               break;
-       case _DRM_CONSISTENT:
-               /* dma_addr_t is 64bit on i386 with CONFIG_HIGHMEM64G,
-                * As we're limiting the address to 2^32-1 (or less),
-                * casting it down to 32 bits is no problem, but we
-                * need to point to a 64bit variable first. */
-               dmah = drm_pci_alloc(dev, map->size, map->size);
-               if (!dmah) {
-                       kfree(map);
-                       return -ENOMEM;
-               }
-               map->handle = dmah->vaddr;
-               map->offset = (unsigned long)dmah->busaddr;
-               kfree(dmah);
-               break;
-       default:
-               kfree(map);
-               return -EINVAL;
-       }
-
-       list = kzalloc(sizeof(*list), GFP_KERNEL);
-       if (!list) {
-               if (map->type == _DRM_REGISTERS)
-                       iounmap(map->handle);
-               kfree(map);
-               return -EINVAL;
-       }
-       list->map = map;
-
-       mutex_lock(&dev->struct_mutex);
-       list_add(&list->head, &dev->maplist);
-
-       /* Assign a 32-bit handle */
-       /* We do it here so that dev->struct_mutex protects the increment */
-       user_token = (map->type == _DRM_SHM) ? (unsigned long)map->handle :
-               map->offset;
-       ret = drm_map_handle(dev, &list->hash, user_token, 0,
-                            (map->type == _DRM_SHM));
-       if (ret) {
-               if (map->type == _DRM_REGISTERS)
-                       iounmap(map->handle);
-               kfree(map);
-               kfree(list);
-               mutex_unlock(&dev->struct_mutex);
-               return ret;
-       }
-
-       list->user_token = list->hash.key << PAGE_SHIFT;
-       mutex_unlock(&dev->struct_mutex);
-
-       if (!(map->flags & _DRM_DRIVER))
-               list->master = dev->primary->master;
-       *maplist = list;
-       return 0;
-       }
-
-int drm_addmap(struct drm_device * dev, resource_size_t offset,
-              unsigned int size, enum drm_map_type type,
-              enum drm_map_flags flags, struct drm_local_map ** map_ptr)
-{
-       struct drm_map_list *list;
-       int rc;
-
-       rc = drm_addmap_core(dev, offset, size, type, flags, &list);
-       if (!rc)
-               *map_ptr = list->map;
-       return rc;
-}
-
-EXPORT_SYMBOL(drm_addmap);
-
-/**
- * Ioctl to specify a range of memory that is available for mapping by a
- * non-root process.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a drm_map structure.
- * \return zero on success or a negative value on error.
- *
- */
-int drm_addmap_ioctl(struct drm_device *dev, void *data,
-                    struct drm_file *file_priv)
-{
-       struct drm_map *map = data;
-       struct drm_map_list *maplist;
-       int err;
-
-       if (!(capable(CAP_SYS_ADMIN) || map->type == _DRM_AGP || map->type == _DRM_SHM))
-               return -EPERM;
-
-       err = drm_addmap_core(dev, map->offset, map->size, map->type,
-                             map->flags, &maplist);
-
-       if (err)
-               return err;
-
-       /* avoid a warning on 64-bit, this casting isn't very nice, but the API is set so too late */
-       map->handle = (void *)(unsigned long)maplist->user_token;
-       return 0;
-}
-
-/**
- * Remove a map private from list and deallocate resources if the mapping
- * isn't in use.
- *
- * Searches the map on drm_device::maplist, removes it from the list, see if
- * its being used, and free any associate resource (such as MTRR's) if it's not
- * being on use.
- *
- * \sa drm_addmap
- */
-int drm_rmmap_locked(struct drm_device *dev, struct drm_local_map *map)
-{
-       struct drm_map_list *r_list = NULL, *list_t;
-       drm_dma_handle_t dmah;
-       int found = 0;
-       struct drm_master *master;
-
-       /* Find the list entry for the map and remove it */
-       list_for_each_entry_safe(r_list, list_t, &dev->maplist, head) {
-               if (r_list->map == map) {
-                       master = r_list->master;
-                       list_del(&r_list->head);
-                       drm_ht_remove_key(&dev->map_hash,
-                                         r_list->user_token >> PAGE_SHIFT);
-                       kfree(r_list);
-                       found = 1;
-                       break;
-               }
-       }
-
-       if (!found)
-               return -EINVAL;
-
-       switch (map->type) {
-       case _DRM_REGISTERS:
-               iounmap(map->handle);
-               /* FALLTHROUGH */
-       case _DRM_FRAME_BUFFER:
-               if (drm_core_has_MTRR(dev) && map->mtrr >= 0) {
-                       int retcode;
-                       retcode = mtrr_del(map->mtrr, map->offset, map->size);
-                       DRM_DEBUG("mtrr_del=%d\n", retcode);
-               }
-               break;
-       case _DRM_SHM:
-               vfree(map->handle);
-               if (master) {
-                       if (dev->sigdata.lock == master->lock.hw_lock)
-                               dev->sigdata.lock = NULL;
-                       master->lock.hw_lock = NULL;   /* SHM removed */
-                       master->lock.file_priv = NULL;
-                       wake_up_interruptible_all(&master->lock.lock_queue);
-               }
-               break;
-       case _DRM_AGP:
-       case _DRM_SCATTER_GATHER:
-               break;
-       case _DRM_CONSISTENT:
-               dmah.vaddr = map->handle;
-               dmah.busaddr = map->offset;
-               dmah.size = map->size;
-               __drm_pci_free(dev, &dmah);
-               break;
-       case _DRM_GEM:
-               DRM_ERROR("tried to rmmap GEM object\n");
-               break;
-       }
-       kfree(map);
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_rmmap_locked);
-
-int drm_rmmap(struct drm_device *dev, struct drm_local_map *map)
-{
-       int ret;
-
-       mutex_lock(&dev->struct_mutex);
-       ret = drm_rmmap_locked(dev, map);
-       mutex_unlock(&dev->struct_mutex);
-
-       return ret;
-}
-EXPORT_SYMBOL(drm_rmmap);
-
-/* The rmmap ioctl appears to be unnecessary.  All mappings are torn down on
- * the last close of the device, and this is necessary for cleanup when things
- * exit uncleanly.  Therefore, having userland manually remove mappings seems
- * like a pointless exercise since they're going away anyway.
- *
- * One use case might be after addmap is allowed for normal users for SHM and
- * gets used by drivers that the server doesn't need to care about.  This seems
- * unlikely.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a struct drm_map structure.
- * \return zero on success or a negative value on error.
- */
-int drm_rmmap_ioctl(struct drm_device *dev, void *data,
-                   struct drm_file *file_priv)
-{
-       struct drm_map *request = data;
-       struct drm_local_map *map = NULL;
-       struct drm_map_list *r_list;
-       int ret;
-
-       mutex_lock(&dev->struct_mutex);
-       list_for_each_entry(r_list, &dev->maplist, head) {
-               if (r_list->map &&
-                   r_list->user_token == (unsigned long)request->handle &&
-                   r_list->map->flags & _DRM_REMOVABLE) {
-                       map = r_list->map;
-                       break;
-               }
-       }
-
-       /* List has wrapped around to the head pointer, or its empty we didn't
-        * find anything.
-        */
-       if (list_empty(&dev->maplist) || !map) {
-               mutex_unlock(&dev->struct_mutex);
-               return -EINVAL;
-       }
-
-       /* Register and framebuffer maps are permanent */
-       if ((map->type == _DRM_REGISTERS) || (map->type == _DRM_FRAME_BUFFER)) {
-               mutex_unlock(&dev->struct_mutex);
-               return 0;
-       }
-
-       ret = drm_rmmap_locked(dev, map);
-
-       mutex_unlock(&dev->struct_mutex);
-
-       return ret;
-}
-
-/**
- * Cleanup after an error on one of the addbufs() functions.
- *
- * \param dev DRM device.
- * \param entry buffer entry where the error occurred.
- *
- * Frees any pages and buffers associated with the given entry.
- */
-static void drm_cleanup_buf_error(struct drm_device * dev,
-                                 struct drm_buf_entry * entry)
-{
-       int i;
-
-       if (entry->seg_count) {
-               for (i = 0; i < entry->seg_count; i++) {
-                       if (entry->seglist[i]) {
-                               drm_pci_free(dev, entry->seglist[i]);
-                       }
-               }
-               kfree(entry->seglist);
-
-               entry->seg_count = 0;
-       }
-
-       if (entry->buf_count) {
-               for (i = 0; i < entry->buf_count; i++) {
-                       kfree(entry->buflist[i].dev_private);
-               }
-               kfree(entry->buflist);
-
-               entry->buf_count = 0;
-       }
-}
-
-#if __OS_HAS_AGP
-/**
- * Add AGP buffers for DMA transfers.
- *
- * \param dev struct drm_device to which the buffers are to be added.
- * \param request pointer to a struct drm_buf_desc describing the request.
- * \return zero on success or a negative number on failure.
- *
- * After some sanity checks creates a drm_buf structure for each buffer and
- * reallocates the buffer list of the same size order to accommodate the new
- * buffers.
- */
-int drm_addbufs_agp(struct drm_device * dev, struct drm_buf_desc * request)
-{
-       struct drm_device_dma *dma = dev->dma;
-       struct drm_buf_entry *entry;
-       struct drm_agp_mem *agp_entry;
-       struct drm_buf *buf;
-       unsigned long offset;
-       unsigned long agp_offset;
-       int count;
-       int order;
-       int size;
-       int alignment;
-       int page_order;
-       int total;
-       int byte_count;
-       int i, valid;
-       struct drm_buf **temp_buflist;
-
-       if (!dma)
-               return -EINVAL;
-
-       count = request->count;
-       order = drm_order(request->size);
-       size = 1 << order;
-
-       alignment = (request->flags & _DRM_PAGE_ALIGN)
-           ? PAGE_ALIGN(size) : size;
-       page_order = order - PAGE_SHIFT > 0 ? order - PAGE_SHIFT : 0;
-       total = PAGE_SIZE << page_order;
-
-       byte_count = 0;
-       agp_offset = dev->agp->base + request->agp_start;
-
-       DRM_DEBUG("count:      %d\n", count);
-       DRM_DEBUG("order:      %d\n", order);
-       DRM_DEBUG("size:       %d\n", size);
-       DRM_DEBUG("agp_offset: %lx\n", agp_offset);
-       DRM_DEBUG("alignment:  %d\n", alignment);
-       DRM_DEBUG("page_order: %d\n", page_order);
-       DRM_DEBUG("total:      %d\n", total);
-
-       if (order < DRM_MIN_ORDER || order > DRM_MAX_ORDER)
-               return -EINVAL;
-       if (dev->queue_count)
-               return -EBUSY;  /* Not while in use */
-
-       /* Make sure buffers are located in AGP memory that we own */
-       valid = 0;
-       list_for_each_entry(agp_entry, &dev->agp->memory, head) {
-               if ((agp_offset >= agp_entry->bound) &&
-                   (agp_offset + total * count <= agp_entry->bound + agp_entry->pages * PAGE_SIZE)) {
-                       valid = 1;
-                       break;
-               }
-       }
-       if (!list_empty(&dev->agp->memory) && !valid) {
-               DRM_DEBUG("zone invalid\n");
-               return -EINVAL;
-       }
-       spin_lock(&dev->count_lock);
-       if (dev->buf_use) {
-               spin_unlock(&dev->count_lock);
-               return -EBUSY;
-       }
-       atomic_inc(&dev->buf_alloc);
-       spin_unlock(&dev->count_lock);
-
-       mutex_lock(&dev->struct_mutex);
-       entry = &dma->bufs[order];
-       if (entry->buf_count) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM; /* May only call once for each order */
-       }
-
-       if (count < 0 || count > 4096) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -EINVAL;
-       }
-
-       entry->buflist = kzalloc(count * sizeof(*entry->buflist), GFP_KERNEL);
-       if (!entry->buflist) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-
-       entry->buf_size = size;
-       entry->page_order = page_order;
-
-       offset = 0;
-
-       while (entry->buf_count < count) {
-               buf = &entry->buflist[entry->buf_count];
-               buf->idx = dma->buf_count + entry->buf_count;
-               buf->total = alignment;
-               buf->order = order;
-               buf->used = 0;
-
-               buf->offset = (dma->byte_count + offset);
-               buf->bus_address = agp_offset + offset;
-               buf->address = (void *)(agp_offset + offset);
-               buf->next = NULL;
-               buf->waiting = 0;
-               buf->pending = 0;
-               init_waitqueue_head(&buf->dma_wait);
-               buf->file_priv = NULL;
-
-               buf->dev_priv_size = dev->driver->dev_priv_size;
-               buf->dev_private = kzalloc(buf->dev_priv_size, GFP_KERNEL);
-               if (!buf->dev_private) {
-                       /* Set count correctly so we free the proper amount. */
-                       entry->buf_count = count;
-                       drm_cleanup_buf_error(dev, entry);
-                       mutex_unlock(&dev->struct_mutex);
-                       atomic_dec(&dev->buf_alloc);
-                       return -ENOMEM;
-               }
-
-               DRM_DEBUG("buffer %d @ %p\n", entry->buf_count, buf->address);
-
-               offset += alignment;
-               entry->buf_count++;
-               byte_count += PAGE_SIZE << page_order;
-       }
-
-       DRM_DEBUG("byte_count: %d\n", byte_count);
-
-       temp_buflist = krealloc(dma->buflist,
-                               (dma->buf_count + entry->buf_count) *
-                               sizeof(*dma->buflist), GFP_KERNEL);
-       if (!temp_buflist) {
-               /* Free the entry because it isn't valid */
-               drm_cleanup_buf_error(dev, entry);
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-       dma->buflist = temp_buflist;
-
-       for (i = 0; i < entry->buf_count; i++) {
-               dma->buflist[i + dma->buf_count] = &entry->buflist[i];
-       }
-
-       dma->buf_count += entry->buf_count;
-       dma->seg_count += entry->seg_count;
-       dma->page_count += byte_count >> PAGE_SHIFT;
-       dma->byte_count += byte_count;
-
-       DRM_DEBUG("dma->buf_count : %d\n", dma->buf_count);
-       DRM_DEBUG("entry->buf_count : %d\n", entry->buf_count);
-
-       mutex_unlock(&dev->struct_mutex);
-
-       request->count = entry->buf_count;
-       request->size = size;
-
-       dma->flags = _DRM_DMA_USE_AGP;
-
-       atomic_dec(&dev->buf_alloc);
-       return 0;
-}
-EXPORT_SYMBOL(drm_addbufs_agp);
-#endif                         /* __OS_HAS_AGP */
-
-int drm_addbufs_pci(struct drm_device * dev, struct drm_buf_desc * request)
-{
-       struct drm_device_dma *dma = dev->dma;
-       int count;
-       int order;
-       int size;
-       int total;
-       int page_order;
-       struct drm_buf_entry *entry;
-       drm_dma_handle_t *dmah;
-       struct drm_buf *buf;
-       int alignment;
-       unsigned long offset;
-       int i;
-       int byte_count;
-       int page_count;
-       unsigned long *temp_pagelist;
-       struct drm_buf **temp_buflist;
-
-       if (!drm_core_check_feature(dev, DRIVER_PCI_DMA))
-               return -EINVAL;
-
-       if (!dma)
-               return -EINVAL;
-
-       if (!capable(CAP_SYS_ADMIN))
-               return -EPERM;
-
-       count = request->count;
-       order = drm_order(request->size);
-       size = 1 << order;
-
-       DRM_DEBUG("count=%d, size=%d (%d), order=%d, queue_count=%d\n",
-                 request->count, request->size, size, order, dev->queue_count);
-
-       if (order < DRM_MIN_ORDER || order > DRM_MAX_ORDER)
-               return -EINVAL;
-       if (dev->queue_count)
-               return -EBUSY;  /* Not while in use */
-
-       alignment = (request->flags & _DRM_PAGE_ALIGN)
-           ? PAGE_ALIGN(size) : size;
-       page_order = order - PAGE_SHIFT > 0 ? order - PAGE_SHIFT : 0;
-       total = PAGE_SIZE << page_order;
-
-       spin_lock(&dev->count_lock);
-       if (dev->buf_use) {
-               spin_unlock(&dev->count_lock);
-               return -EBUSY;
-       }
-       atomic_inc(&dev->buf_alloc);
-       spin_unlock(&dev->count_lock);
-
-       mutex_lock(&dev->struct_mutex);
-       entry = &dma->bufs[order];
-       if (entry->buf_count) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM; /* May only call once for each order */
-       }
-
-       if (count < 0 || count > 4096) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -EINVAL;
-       }
-
-       entry->buflist = kzalloc(count * sizeof(*entry->buflist), GFP_KERNEL);
-       if (!entry->buflist) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-
-       entry->seglist = kzalloc(count * sizeof(*entry->seglist), GFP_KERNEL);
-       if (!entry->seglist) {
-               kfree(entry->buflist);
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-
-       /* Keep the original pagelist until we know all the allocations
-        * have succeeded
-        */
-       temp_pagelist = kmalloc((dma->page_count + (count << page_order)) *
-                              sizeof(*dma->pagelist), GFP_KERNEL);
-       if (!temp_pagelist) {
-               kfree(entry->buflist);
-               kfree(entry->seglist);
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-       memcpy(temp_pagelist,
-              dma->pagelist, dma->page_count * sizeof(*dma->pagelist));
-       DRM_DEBUG("pagelist: %d entries\n",
-                 dma->page_count + (count << page_order));
-
-       entry->buf_size = size;
-       entry->page_order = page_order;
-       byte_count = 0;
-       page_count = 0;
-
-       while (entry->buf_count < count) {
-
-               dmah = drm_pci_alloc(dev, PAGE_SIZE << page_order, 0x1000);
-
-               if (!dmah) {
-                       /* Set count correctly so we free the proper amount. */
-                       entry->buf_count = count;
-                       entry->seg_count = count;
-                       drm_cleanup_buf_error(dev, entry);
-                       kfree(temp_pagelist);
-                       mutex_unlock(&dev->struct_mutex);
-                       atomic_dec(&dev->buf_alloc);
-                       return -ENOMEM;
-               }
-               entry->seglist[entry->seg_count++] = dmah;
-               for (i = 0; i < (1 << page_order); i++) {
-                       DRM_DEBUG("page %d @ 0x%08lx\n",
-                                 dma->page_count + page_count,
-                                 (unsigned long)dmah->vaddr + PAGE_SIZE * i);
-                       temp_pagelist[dma->page_count + page_count++]
-                               = (unsigned long)dmah->vaddr + PAGE_SIZE * i;
-               }
-               for (offset = 0;
-                    offset + size <= total && entry->buf_count < count;
-                    offset += alignment, ++entry->buf_count) {
-                       buf = &entry->buflist[entry->buf_count];
-                       buf->idx = dma->buf_count + entry->buf_count;
-                       buf->total = alignment;
-                       buf->order = order;
-                       buf->used = 0;
-                       buf->offset = (dma->byte_count + byte_count + offset);
-                       buf->address = (void *)(dmah->vaddr + offset);
-                       buf->bus_address = dmah->busaddr + offset;
-                       buf->next = NULL;
-                       buf->waiting = 0;
-                       buf->pending = 0;
-                       init_waitqueue_head(&buf->dma_wait);
-                       buf->file_priv = NULL;
-
-                       buf->dev_priv_size = dev->driver->dev_priv_size;
-                       buf->dev_private = kzalloc(buf->dev_priv_size,
-                                               GFP_KERNEL);
-                       if (!buf->dev_private) {
-                               /* Set count correctly so we free the proper amount. */
-                               entry->buf_count = count;
-                               entry->seg_count = count;
-                               drm_cleanup_buf_error(dev, entry);
-                               kfree(temp_pagelist);
-                               mutex_unlock(&dev->struct_mutex);
-                               atomic_dec(&dev->buf_alloc);
-                               return -ENOMEM;
-                       }
-
-                       DRM_DEBUG("buffer %d @ %p\n",
-                                 entry->buf_count, buf->address);
-               }
-               byte_count += PAGE_SIZE << page_order;
-       }
-
-       temp_buflist = krealloc(dma->buflist,
-                               (dma->buf_count + entry->buf_count) *
-                               sizeof(*dma->buflist), GFP_KERNEL);
-       if (!temp_buflist) {
-               /* Free the entry because it isn't valid */
-               drm_cleanup_buf_error(dev, entry);
-               kfree(temp_pagelist);
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-       dma->buflist = temp_buflist;
-
-       for (i = 0; i < entry->buf_count; i++) {
-               dma->buflist[i + dma->buf_count] = &entry->buflist[i];
-       }
-
-       /* No allocations failed, so now we can replace the original pagelist
-        * with the new one.
-        */
-       if (dma->page_count) {
-               kfree(dma->pagelist);
-       }
-       dma->pagelist = temp_pagelist;
-
-       dma->buf_count += entry->buf_count;
-       dma->seg_count += entry->seg_count;
-       dma->page_count += entry->seg_count << page_order;
-       dma->byte_count += PAGE_SIZE * (entry->seg_count << page_order);
-
-       mutex_unlock(&dev->struct_mutex);
-
-       request->count = entry->buf_count;
-       request->size = size;
-
-       if (request->flags & _DRM_PCI_BUFFER_RO)
-               dma->flags = _DRM_DMA_USE_PCI_RO;
-
-       atomic_dec(&dev->buf_alloc);
-       return 0;
-
-}
-EXPORT_SYMBOL(drm_addbufs_pci);
-
-static int drm_addbufs_sg(struct drm_device * dev, struct drm_buf_desc * request)
-{
-       struct drm_device_dma *dma = dev->dma;
-       struct drm_buf_entry *entry;
-       struct drm_buf *buf;
-       unsigned long offset;
-       unsigned long agp_offset;
-       int count;
-       int order;
-       int size;
-       int alignment;
-       int page_order;
-       int total;
-       int byte_count;
-       int i;
-       struct drm_buf **temp_buflist;
-
-       if (!drm_core_check_feature(dev, DRIVER_SG))
-               return -EINVAL;
-
-       if (!dma)
-               return -EINVAL;
-
-       if (!capable(CAP_SYS_ADMIN))
-               return -EPERM;
-
-       count = request->count;
-       order = drm_order(request->size);
-       size = 1 << order;
-
-       alignment = (request->flags & _DRM_PAGE_ALIGN)
-           ? PAGE_ALIGN(size) : size;
-       page_order = order - PAGE_SHIFT > 0 ? order - PAGE_SHIFT : 0;
-       total = PAGE_SIZE << page_order;
-
-       byte_count = 0;
-       agp_offset = request->agp_start;
-
-       DRM_DEBUG("count:      %d\n", count);
-       DRM_DEBUG("order:      %d\n", order);
-       DRM_DEBUG("size:       %d\n", size);
-       DRM_DEBUG("agp_offset: %lu\n", agp_offset);
-       DRM_DEBUG("alignment:  %d\n", alignment);
-       DRM_DEBUG("page_order: %d\n", page_order);
-       DRM_DEBUG("total:      %d\n", total);
-
-       if (order < DRM_MIN_ORDER || order > DRM_MAX_ORDER)
-               return -EINVAL;
-       if (dev->queue_count)
-               return -EBUSY;  /* Not while in use */
-
-       spin_lock(&dev->count_lock);
-       if (dev->buf_use) {
-               spin_unlock(&dev->count_lock);
-               return -EBUSY;
-       }
-       atomic_inc(&dev->buf_alloc);
-       spin_unlock(&dev->count_lock);
-
-       mutex_lock(&dev->struct_mutex);
-       entry = &dma->bufs[order];
-       if (entry->buf_count) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM; /* May only call once for each order */
-       }
-
-       if (count < 0 || count > 4096) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -EINVAL;
-       }
-
-       entry->buflist = kzalloc(count * sizeof(*entry->buflist),
-                               GFP_KERNEL);
-       if (!entry->buflist) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-
-       entry->buf_size = size;
-       entry->page_order = page_order;
-
-       offset = 0;
-
-       while (entry->buf_count < count) {
-               buf = &entry->buflist[entry->buf_count];
-               buf->idx = dma->buf_count + entry->buf_count;
-               buf->total = alignment;
-               buf->order = order;
-               buf->used = 0;
-
-               buf->offset = (dma->byte_count + offset);
-               buf->bus_address = agp_offset + offset;
-               buf->address = (void *)(agp_offset + offset
-                                       + (unsigned long)dev->sg->virtual);
-               buf->next = NULL;
-               buf->waiting = 0;
-               buf->pending = 0;
-               init_waitqueue_head(&buf->dma_wait);
-               buf->file_priv = NULL;
-
-               buf->dev_priv_size = dev->driver->dev_priv_size;
-               buf->dev_private = kzalloc(buf->dev_priv_size, GFP_KERNEL);
-               if (!buf->dev_private) {
-                       /* Set count correctly so we free the proper amount. */
-                       entry->buf_count = count;
-                       drm_cleanup_buf_error(dev, entry);
-                       mutex_unlock(&dev->struct_mutex);
-                       atomic_dec(&dev->buf_alloc);
-                       return -ENOMEM;
-               }
-
-               DRM_DEBUG("buffer %d @ %p\n", entry->buf_count, buf->address);
-
-               offset += alignment;
-               entry->buf_count++;
-               byte_count += PAGE_SIZE << page_order;
-       }
-
-       DRM_DEBUG("byte_count: %d\n", byte_count);
-
-       temp_buflist = krealloc(dma->buflist,
-                               (dma->buf_count + entry->buf_count) *
-                               sizeof(*dma->buflist), GFP_KERNEL);
-       if (!temp_buflist) {
-               /* Free the entry because it isn't valid */
-               drm_cleanup_buf_error(dev, entry);
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-       dma->buflist = temp_buflist;
-
-       for (i = 0; i < entry->buf_count; i++) {
-               dma->buflist[i + dma->buf_count] = &entry->buflist[i];
-       }
-
-       dma->buf_count += entry->buf_count;
-       dma->seg_count += entry->seg_count;
-       dma->page_count += byte_count >> PAGE_SHIFT;
-       dma->byte_count += byte_count;
-
-       DRM_DEBUG("dma->buf_count : %d\n", dma->buf_count);
-       DRM_DEBUG("entry->buf_count : %d\n", entry->buf_count);
-
-       mutex_unlock(&dev->struct_mutex);
-
-       request->count = entry->buf_count;
-       request->size = size;
-
-       dma->flags = _DRM_DMA_USE_SG;
-
-       atomic_dec(&dev->buf_alloc);
-       return 0;
-}
-
-static int drm_addbufs_fb(struct drm_device * dev, struct drm_buf_desc * request)
-{
-       struct drm_device_dma *dma = dev->dma;
-       struct drm_buf_entry *entry;
-       struct drm_buf *buf;
-       unsigned long offset;
-       unsigned long agp_offset;
-       int count;
-       int order;
-       int size;
-       int alignment;
-       int page_order;
-       int total;
-       int byte_count;
-       int i;
-       struct drm_buf **temp_buflist;
-
-       if (!drm_core_check_feature(dev, DRIVER_FB_DMA))
-               return -EINVAL;
-
-       if (!dma)
-               return -EINVAL;
-
-       if (!capable(CAP_SYS_ADMIN))
-               return -EPERM;
-
-       count = request->count;
-       order = drm_order(request->size);
-       size = 1 << order;
-
-       alignment = (request->flags & _DRM_PAGE_ALIGN)
-           ? PAGE_ALIGN(size) : size;
-       page_order = order - PAGE_SHIFT > 0 ? order - PAGE_SHIFT : 0;
-       total = PAGE_SIZE << page_order;
-
-       byte_count = 0;
-       agp_offset = request->agp_start;
-
-       DRM_DEBUG("count:      %d\n", count);
-       DRM_DEBUG("order:      %d\n", order);
-       DRM_DEBUG("size:       %d\n", size);
-       DRM_DEBUG("agp_offset: %lu\n", agp_offset);
-       DRM_DEBUG("alignment:  %d\n", alignment);
-       DRM_DEBUG("page_order: %d\n", page_order);
-       DRM_DEBUG("total:      %d\n", total);
-
-       if (order < DRM_MIN_ORDER || order > DRM_MAX_ORDER)
-               return -EINVAL;
-       if (dev->queue_count)
-               return -EBUSY;  /* Not while in use */
-
-       spin_lock(&dev->count_lock);
-       if (dev->buf_use) {
-               spin_unlock(&dev->count_lock);
-               return -EBUSY;
-       }
-       atomic_inc(&dev->buf_alloc);
-       spin_unlock(&dev->count_lock);
-
-       mutex_lock(&dev->struct_mutex);
-       entry = &dma->bufs[order];
-       if (entry->buf_count) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM; /* May only call once for each order */
-       }
-
-       if (count < 0 || count > 4096) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -EINVAL;
-       }
-
-       entry->buflist = kzalloc(count * sizeof(*entry->buflist),
-                               GFP_KERNEL);
-       if (!entry->buflist) {
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-
-       entry->buf_size = size;
-       entry->page_order = page_order;
-
-       offset = 0;
-
-       while (entry->buf_count < count) {
-               buf = &entry->buflist[entry->buf_count];
-               buf->idx = dma->buf_count + entry->buf_count;
-               buf->total = alignment;
-               buf->order = order;
-               buf->used = 0;
-
-               buf->offset = (dma->byte_count + offset);
-               buf->bus_address = agp_offset + offset;
-               buf->address = (void *)(agp_offset + offset);
-               buf->next = NULL;
-               buf->waiting = 0;
-               buf->pending = 0;
-               init_waitqueue_head(&buf->dma_wait);
-               buf->file_priv = NULL;
-
-               buf->dev_priv_size = dev->driver->dev_priv_size;
-               buf->dev_private = kzalloc(buf->dev_priv_size, GFP_KERNEL);
-               if (!buf->dev_private) {
-                       /* Set count correctly so we free the proper amount. */
-                       entry->buf_count = count;
-                       drm_cleanup_buf_error(dev, entry);
-                       mutex_unlock(&dev->struct_mutex);
-                       atomic_dec(&dev->buf_alloc);
-                       return -ENOMEM;
-               }
-
-               DRM_DEBUG("buffer %d @ %p\n", entry->buf_count, buf->address);
-
-               offset += alignment;
-               entry->buf_count++;
-               byte_count += PAGE_SIZE << page_order;
-       }
-
-       DRM_DEBUG("byte_count: %d\n", byte_count);
-
-       temp_buflist = krealloc(dma->buflist,
-                               (dma->buf_count + entry->buf_count) *
-                               sizeof(*dma->buflist), GFP_KERNEL);
-       if (!temp_buflist) {
-               /* Free the entry because it isn't valid */
-               drm_cleanup_buf_error(dev, entry);
-               mutex_unlock(&dev->struct_mutex);
-               atomic_dec(&dev->buf_alloc);
-               return -ENOMEM;
-       }
-       dma->buflist = temp_buflist;
-
-       for (i = 0; i < entry->buf_count; i++) {
-               dma->buflist[i + dma->buf_count] = &entry->buflist[i];
-       }
-
-       dma->buf_count += entry->buf_count;
-       dma->seg_count += entry->seg_count;
-       dma->page_count += byte_count >> PAGE_SHIFT;
-       dma->byte_count += byte_count;
-
-       DRM_DEBUG("dma->buf_count : %d\n", dma->buf_count);
-       DRM_DEBUG("entry->buf_count : %d\n", entry->buf_count);
-
-       mutex_unlock(&dev->struct_mutex);
-
-       request->count = entry->buf_count;
-       request->size = size;
-
-       dma->flags = _DRM_DMA_USE_FB;
-
-       atomic_dec(&dev->buf_alloc);
-       return 0;
-}
-
-
-/**
- * Add buffers for DMA transfers (ioctl).
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a struct drm_buf_desc request.
- * \return zero on success or a negative number on failure.
- *
- * According with the memory type specified in drm_buf_desc::flags and the
- * build options, it dispatches the call either to addbufs_agp(),
- * addbufs_sg() or addbufs_pci() for AGP, scatter-gather or consistent
- * PCI memory respectively.
- */
-int drm_addbufs(struct drm_device *dev, void *data,
-               struct drm_file *file_priv)
-{
-       struct drm_buf_desc *request = data;
-       int ret;
-
-       if (!drm_core_check_feature(dev, DRIVER_HAVE_DMA))
-               return -EINVAL;
-
-#if __OS_HAS_AGP
-       if (request->flags & _DRM_AGP_BUFFER)
-               ret = drm_addbufs_agp(dev, request);
-       else
-#endif
-       if (request->flags & _DRM_SG_BUFFER)
-               ret = drm_addbufs_sg(dev, request);
-       else if (request->flags & _DRM_FB_BUFFER)
-               ret = drm_addbufs_fb(dev, request);
-       else
-               ret = drm_addbufs_pci(dev, request);
-
-       return ret;
-}
-
-/**
- * Get information about the buffer mappings.
- *
- * This was originally mean for debugging purposes, or by a sophisticated
- * client library to determine how best to use the available buffers (e.g.,
- * large buffers can be used for image transfer).
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a drm_buf_info structure.
- * \return zero on success or a negative number on failure.
- *
- * Increments drm_device::buf_use while holding the drm_device::count_lock
- * lock, preventing of allocating more buffers after this call. Information
- * about each requested buffer is then copied into user space.
- */
-int drm_infobufs(struct drm_device *dev, void *data,
-                struct drm_file *file_priv)
-{
-       struct drm_device_dma *dma = dev->dma;
-       struct drm_buf_info *request = data;
-       int i;
-       int count;
-
-       if (!drm_core_check_feature(dev, DRIVER_HAVE_DMA))
-               return -EINVAL;
-
-       if (!dma)
-               return -EINVAL;
-
-       spin_lock(&dev->count_lock);
-       if (atomic_read(&dev->buf_alloc)) {
-               spin_unlock(&dev->count_lock);
-               return -EBUSY;
-       }
-       ++dev->buf_use;         /* Can't allocate more after this call */
-       spin_unlock(&dev->count_lock);
-
-       for (i = 0, count = 0; i < DRM_MAX_ORDER + 1; i++) {
-               if (dma->bufs[i].buf_count)
-                       ++count;
-       }
-
-       DRM_DEBUG("count = %d\n", count);
-
-       if (request->count >= count) {
-               for (i = 0, count = 0; i < DRM_MAX_ORDER + 1; i++) {
-                       if (dma->bufs[i].buf_count) {
-                               struct drm_buf_desc __user *to =
-                                   &request->list[count];
-                               struct drm_buf_entry *from = &dma->bufs[i];
-                               struct drm_freelist *list = &dma->bufs[i].freelist;
-                               if (copy_to_user(&to->count,
-                                                &from->buf_count,
-                                                sizeof(from->buf_count)) ||
-                                   copy_to_user(&to->size,
-                                                &from->buf_size,
-                                                sizeof(from->buf_size)) ||
-                                   copy_to_user(&to->low_mark,
-                                                &list->low_mark,
-                                                sizeof(list->low_mark)) ||
-                                   copy_to_user(&to->high_mark,
-                                                &list->high_mark,
-                                                sizeof(list->high_mark)))
-                                       return -EFAULT;
-
-                               DRM_DEBUG("%d %d %d %d %d\n",
-                                         i,
-                                         dma->bufs[i].buf_count,
-                                         dma->bufs[i].buf_size,
-                                         dma->bufs[i].freelist.low_mark,
-                                         dma->bufs[i].freelist.high_mark);
-                               ++count;
-                       }
-               }
-       }
-       request->count = count;
-
-       return 0;
-}
-
-/**
- * Specifies a low and high water mark for buffer allocation
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg a pointer to a drm_buf_desc structure.
- * \return zero on success or a negative number on failure.
- *
- * Verifies that the size order is bounded between the admissible orders and
- * updates the respective drm_device_dma::bufs entry low and high water mark.
- *
- * \note This ioctl is deprecated and mostly never used.
- */
-int drm_markbufs(struct drm_device *dev, void *data,
-                struct drm_file *file_priv)
-{
-       struct drm_device_dma *dma = dev->dma;
-       struct drm_buf_desc *request = data;
-       int order;
-       struct drm_buf_entry *entry;
-
-       if (!drm_core_check_feature(dev, DRIVER_HAVE_DMA))
-               return -EINVAL;
-
-       if (!dma)
-               return -EINVAL;
-
-       DRM_DEBUG("%d, %d, %d\n",
-                 request->size, request->low_mark, request->high_mark);
-       order = drm_order(request->size);
-       if (order < DRM_MIN_ORDER || order > DRM_MAX_ORDER)
-               return -EINVAL;
-       entry = &dma->bufs[order];
-
-       if (request->low_mark < 0 || request->low_mark > entry->buf_count)
-               return -EINVAL;
-       if (request->high_mark < 0 || request->high_mark > entry->buf_count)
-               return -EINVAL;
-
-       entry->freelist.low_mark = request->low_mark;
-       entry->freelist.high_mark = request->high_mark;
-
-       return 0;
-}
-
-/**
- * Unreserve the buffers in list, previously reserved using drmDMA.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a drm_buf_free structure.
- * \return zero on success or a negative number on failure.
- *
- * Calls free_buffer() for each used buffer.
- * This function is primarily used for debugging.
- */
-int drm_freebufs(struct drm_device *dev, void *data,
-                struct drm_file *file_priv)
-{
-       struct drm_device_dma *dma = dev->dma;
-       struct drm_buf_free *request = data;
-       int i;
-       int idx;
-       struct drm_buf *buf;
-
-       if (!drm_core_check_feature(dev, DRIVER_HAVE_DMA))
-               return -EINVAL;
-
-       if (!dma)
-               return -EINVAL;
-
-       DRM_DEBUG("%d\n", request->count);
-       for (i = 0; i < request->count; i++) {
-               if (copy_from_user(&idx, &request->list[i], sizeof(idx)))
-                       return -EFAULT;
-               if (idx < 0 || idx >= dma->buf_count) {
-                       DRM_ERROR("Index %d (of %d max)\n",
-                                 idx, dma->buf_count - 1);
-                       return -EINVAL;
-               }
-               buf = dma->buflist[idx];
-               if (buf->file_priv != file_priv) {
-                       DRM_ERROR("Process %d freeing buffer not owned\n",
-                                 task_pid_nr(current));
-                       return -EINVAL;
-               }
-               drm_free_buffer(dev, buf);
-       }
-
-       return 0;
-}
-
-/**
- * Maps all of the DMA buffers into client-virtual space (ioctl).
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg pointer to a drm_buf_map structure.
- * \return zero on success or a negative number on failure.
- *
- * Maps the AGP, SG or PCI buffer region with do_mmap(), and copies information
- * about each buffer into user space. For PCI buffers, it calls do_mmap() with
- * offset equal to 0, which drm_mmap() interpretes as PCI buffers and calls
- * drm_mmap_dma().
- */
-int drm_mapbufs(struct drm_device *dev, void *data,
-               struct drm_file *file_priv)
-{
-       struct drm_device_dma *dma = dev->dma;
-       int retcode = 0;
-       const int zero = 0;
-       unsigned long virtual;
-       unsigned long address;
-       struct drm_buf_map *request = data;
-       int i;
-
-       if (!drm_core_check_feature(dev, DRIVER_HAVE_DMA))
-               return -EINVAL;
-
-       if (!dma)
-               return -EINVAL;
-
-       spin_lock(&dev->count_lock);
-       if (atomic_read(&dev->buf_alloc)) {
-               spin_unlock(&dev->count_lock);
-               return -EBUSY;
-       }
-       dev->buf_use++;         /* Can't allocate more after this call */
-       spin_unlock(&dev->count_lock);
-
-       if (request->count >= dma->buf_count) {
-               if ((drm_core_has_AGP(dev) && (dma->flags & _DRM_DMA_USE_AGP))
-                   || (drm_core_check_feature(dev, DRIVER_SG)
-                       && (dma->flags & _DRM_DMA_USE_SG))
-                   || (drm_core_check_feature(dev, DRIVER_FB_DMA)
-                       && (dma->flags & _DRM_DMA_USE_FB))) {
-                       struct drm_local_map *map = dev->agp_buffer_map;
-                       unsigned long token = dev->agp_buffer_token;
-
-                       if (!map) {
-                               retcode = -EINVAL;
-                               goto done;
-                       }
-                       down_write(&current->mm->mmap_sem);
-                       virtual = do_mmap(file_priv->filp, 0, map->size,
-                                         PROT_READ | PROT_WRITE,
-                                         MAP_SHARED,
-                                         token);
-                       up_write(&current->mm->mmap_sem);
-               } else {
-                       down_write(&current->mm->mmap_sem);
-                       virtual = do_mmap(file_priv->filp, 0, dma->byte_count,
-                                         PROT_READ | PROT_WRITE,
-                                         MAP_SHARED, 0);
-                       up_write(&current->mm->mmap_sem);
-               }
-               if (virtual > -1024UL) {
-                       /* Real error */
-                       retcode = (signed long)virtual;
-                       goto done;
-               }
-               request->virtual = (void __user *)virtual;
-
-               for (i = 0; i < dma->buf_count; i++) {
-                       if (copy_to_user(&request->list[i].idx,
-                                        &dma->buflist[i]->idx,
-                                        sizeof(request->list[0].idx))) {
-                               retcode = -EFAULT;
-                               goto done;
-                       }
-                       if (copy_to_user(&request->list[i].total,
-                                        &dma->buflist[i]->total,
-                                        sizeof(request->list[0].total))) {
-                               retcode = -EFAULT;
-                               goto done;
-                       }
-                       if (copy_to_user(&request->list[i].used,
-                                        &zero, sizeof(zero))) {
-                               retcode = -EFAULT;
-                               goto done;
-                       }
-                       address = virtual + dma->buflist[i]->offset;    /* *** */
-                       if (copy_to_user(&request->list[i].address,
-                                        &address, sizeof(address))) {
-                               retcode = -EFAULT;
-                               goto done;
-                       }
-               }
-       }
-      done:
-       request->count = dma->buf_count;
-       DRM_DEBUG("%d buffers, retcode = %d\n", request->count, retcode);
-
-       return retcode;
-}
-
-/**
- * Compute size order.  Returns the exponent of the smaller power of two which
- * is greater or equal to given number.
- *
- * \param size size.
- * \return order.
- *
- * \todo Can be made faster.
- */
-int drm_order(unsigned long size)
-{
-       int order;
-       unsigned long tmp;
-
-       for (order = 0, tmp = size >> 1; tmp; tmp >>= 1, order++) ;
-
-       if (size & (size - 1))
-               ++order;
-
-       return order;
-}
-EXPORT_SYMBOL(drm_order);
diff --git a/services4/3rdparty/linux_drm/drm_cache.c b/services4/3rdparty/linux_drm/drm_cache.c
deleted file mode 100644 (file)
index 0e3bd5b..0000000
+++ /dev/null
@@ -1,99 +0,0 @@
-/**************************************************************************
- *
- * Copyright (c) 2006-2007 Tungsten Graphics, Inc., Cedar Park, TX., USA
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sub license, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice (including the
- * next paragraph) shall be included in all copies or substantial portions
- * of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
- * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
- * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
- * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
- * USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- **************************************************************************/
-/*
- * Authors: Thomas Hellström <thomas-at-tungstengraphics-dot-com>
- */
-
-#include "drmP.h"
-
-#if defined(CONFIG_X86)
-static void
-drm_clflush_page(struct page *page)
-{
-       uint8_t *page_virtual;
-       unsigned int i;
-
-       if (unlikely(page == NULL))
-               return;
-
-       page_virtual = kmap_atomic(page, KM_USER0);
-       for (i = 0; i < PAGE_SIZE; i += boot_cpu_data.x86_clflush_size)
-               clflush(page_virtual + i);
-       kunmap_atomic(page_virtual, KM_USER0);
-}
-
-static void drm_cache_flush_clflush(struct page *pages[],
-                                   unsigned long num_pages)
-{
-       unsigned long i;
-
-       mb();
-       for (i = 0; i < num_pages; i++)
-               drm_clflush_page(*pages++);
-       mb();
-}
-
-static void
-drm_clflush_ipi_handler(void *null)
-{
-       wbinvd();
-}
-#endif
-
-void
-drm_clflush_pages(struct page *pages[], unsigned long num_pages)
-{
-
-#if defined(CONFIG_X86)
-       if (cpu_has_clflush) {
-               drm_cache_flush_clflush(pages, num_pages);
-               return;
-       }
-
-       if (on_each_cpu(drm_clflush_ipi_handler, NULL, 1) != 0)
-               printk(KERN_ERR "Timed out waiting for cache flush.\n");
-
-#elif defined(__powerpc__)
-       unsigned long i;
-       for (i = 0; i < num_pages; i++) {
-               struct page *page = pages[i];
-               void *page_virtual;
-
-               if (unlikely(page == NULL))
-                       continue;
-
-               page_virtual = kmap_atomic(page, KM_USER0);
-               flush_dcache_range((unsigned long)page_virtual,
-                                  (unsigned long)page_virtual + PAGE_SIZE);
-               kunmap_atomic(page_virtual, KM_USER0);
-       }
-#else
-       printk(KERN_ERR "Architecture has no drm_cache.c support\n");
-       WARN_ON_ONCE(1);
-#endif
-}
-EXPORT_SYMBOL(drm_clflush_pages);
diff --git a/services4/3rdparty/linux_drm/drm_context.c b/services4/3rdparty/linux_drm/drm_context.c
deleted file mode 100644 (file)
index 6d440fb..0000000
+++ /dev/null
@@ -1,461 +0,0 @@
-/**
- * \file drm_context.c
- * IOCTLs for generic contexts
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Fri Nov 24 18:31:37 2000 by gareth@valinux.com
- *
- * Copyright 1999, 2000 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-/*
- * ChangeLog:
- *  2001-11-16 Torsten Duwe <duwe@caldera.de>
- *             added context constructor/destructor hooks,
- *             needed by SiS driver's memory management.
- */
-
-#include "drmP.h"
-
-/******************************************************************/
-/** \name Context bitmap support */
-/*@{*/
-
-/**
- * Free a handle from the context bitmap.
- *
- * \param dev DRM device.
- * \param ctx_handle context handle.
- *
- * Clears the bit specified by \p ctx_handle in drm_device::ctx_bitmap and the entry
- * in drm_device::ctx_idr, while holding the drm_device::struct_mutex
- * lock.
- */
-void drm_ctxbitmap_free(struct drm_device * dev, int ctx_handle)
-{
-       mutex_lock(&dev->struct_mutex);
-       idr_remove(&dev->ctx_idr, ctx_handle);
-       mutex_unlock(&dev->struct_mutex);
-}
-
-/**
- * Context bitmap allocation.
- *
- * \param dev DRM device.
- * \return (non-negative) context handle on success or a negative number on failure.
- *
- * Allocate a new idr from drm_device::ctx_idr while holding the
- * drm_device::struct_mutex lock.
- */
-static int drm_ctxbitmap_next(struct drm_device * dev)
-{
-       int new_id;
-       int ret;
-
-again:
-       if (idr_pre_get(&dev->ctx_idr, GFP_KERNEL) == 0) {
-               DRM_ERROR("Out of memory expanding drawable idr\n");
-               return -ENOMEM;
-       }
-       mutex_lock(&dev->struct_mutex);
-       ret = idr_get_new_above(&dev->ctx_idr, NULL,
-                               DRM_RESERVED_CONTEXTS, &new_id);
-       if (ret == -EAGAIN) {
-               mutex_unlock(&dev->struct_mutex);
-               goto again;
-       }
-       mutex_unlock(&dev->struct_mutex);
-       return new_id;
-}
-
-/**
- * Context bitmap initialization.
- *
- * \param dev DRM device.
- *
- * Initialise the drm_device::ctx_idr
- */
-int drm_ctxbitmap_init(struct drm_device * dev)
-{
-       idr_init(&dev->ctx_idr);
-       return 0;
-}
-
-/**
- * Context bitmap cleanup.
- *
- * \param dev DRM device.
- *
- * Free all idr members using drm_ctx_sarea_free helper function
- * while holding the drm_device::struct_mutex lock.
- */
-void drm_ctxbitmap_cleanup(struct drm_device * dev)
-{
-       mutex_lock(&dev->struct_mutex);
-       idr_remove_all(&dev->ctx_idr);
-       mutex_unlock(&dev->struct_mutex);
-}
-
-/*@}*/
-
-/******************************************************************/
-/** \name Per Context SAREA Support */
-/*@{*/
-
-/**
- * Get per-context SAREA.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument pointing to a drm_ctx_priv_map structure.
- * \return zero on success or a negative number on failure.
- *
- * Gets the map from drm_device::ctx_idr with the handle specified and
- * returns its handle.
- */
-int drm_getsareactx(struct drm_device *dev, void *data,
-                   struct drm_file *file_priv)
-{
-       struct drm_ctx_priv_map *request = data;
-       struct drm_local_map *map;
-       struct drm_map_list *_entry;
-
-       mutex_lock(&dev->struct_mutex);
-
-       map = idr_find(&dev->ctx_idr, request->ctx_id);
-       if (!map) {
-               mutex_unlock(&dev->struct_mutex);
-               return -EINVAL;
-       }
-
-       mutex_unlock(&dev->struct_mutex);
-
-       request->handle = NULL;
-       list_for_each_entry(_entry, &dev->maplist, head) {
-               if (_entry->map == map) {
-                       request->handle =
-                           (void *)(unsigned long)_entry->user_token;
-                       break;
-               }
-       }
-       if (request->handle == NULL)
-               return -EINVAL;
-
-       return 0;
-}
-
-/**
- * Set per-context SAREA.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument pointing to a drm_ctx_priv_map structure.
- * \return zero on success or a negative number on failure.
- *
- * Searches the mapping specified in \p arg and update the entry in
- * drm_device::ctx_idr with it.
- */
-int drm_setsareactx(struct drm_device *dev, void *data,
-                   struct drm_file *file_priv)
-{
-       struct drm_ctx_priv_map *request = data;
-       struct drm_local_map *map = NULL;
-       struct drm_map_list *r_list = NULL;
-
-       mutex_lock(&dev->struct_mutex);
-       list_for_each_entry(r_list, &dev->maplist, head) {
-               if (r_list->map
-                   && r_list->user_token == (unsigned long) request->handle)
-                       goto found;
-       }
-      bad:
-       mutex_unlock(&dev->struct_mutex);
-       return -EINVAL;
-
-      found:
-       map = r_list->map;
-       if (!map)
-               goto bad;
-
-       if (IS_ERR(idr_replace(&dev->ctx_idr, map, request->ctx_id)))
-               goto bad;
-
-       mutex_unlock(&dev->struct_mutex);
-
-       return 0;
-}
-
-/*@}*/
-
-/******************************************************************/
-/** \name The actual DRM context handling routines */
-/*@{*/
-
-/**
- * Switch context.
- *
- * \param dev DRM device.
- * \param old old context handle.
- * \param new new context handle.
- * \return zero on success or a negative number on failure.
- *
- * Attempt to set drm_device::context_flag.
- */
-static int drm_context_switch(struct drm_device * dev, int old, int new)
-{
-       if (test_and_set_bit(0, &dev->context_flag)) {
-               DRM_ERROR("Reentering -- FIXME\n");
-               return -EBUSY;
-       }
-
-       DRM_DEBUG("Context switch from %d to %d\n", old, new);
-
-       if (new == dev->last_context) {
-               clear_bit(0, &dev->context_flag);
-               return 0;
-       }
-
-       return 0;
-}
-
-/**
- * Complete context switch.
- *
- * \param dev DRM device.
- * \param new new context handle.
- * \return zero on success or a negative number on failure.
- *
- * Updates drm_device::last_context and drm_device::last_switch. Verifies the
- * hardware lock is held, clears the drm_device::context_flag and wakes up
- * drm_device::context_wait.
- */
-static int drm_context_switch_complete(struct drm_device *dev,
-                                      struct drm_file *file_priv, int new)
-{
-       dev->last_context = new;        /* PRE/POST: This is the _only_ writer. */
-       dev->last_switch = jiffies;
-
-       if (!_DRM_LOCK_IS_HELD(file_priv->master->lock.hw_lock->lock)) {
-               DRM_ERROR("Lock isn't held after context switch\n");
-       }
-
-       /* If a context switch is ever initiated
-          when the kernel holds the lock, release
-          that lock here. */
-       clear_bit(0, &dev->context_flag);
-       wake_up(&dev->context_wait);
-
-       return 0;
-}
-
-/**
- * Reserve contexts.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument pointing to a drm_ctx_res structure.
- * \return zero on success or a negative number on failure.
- */
-int drm_resctx(struct drm_device *dev, void *data,
-              struct drm_file *file_priv)
-{
-       struct drm_ctx_res *res = data;
-       struct drm_ctx ctx;
-       int i;
-
-       if (res->count >= DRM_RESERVED_CONTEXTS) {
-               memset(&ctx, 0, sizeof(ctx));
-               for (i = 0; i < DRM_RESERVED_CONTEXTS; i++) {
-                       ctx.handle = i;
-                       if (copy_to_user(&res->contexts[i], &ctx, sizeof(ctx)))
-                               return -EFAULT;
-               }
-       }
-       res->count = DRM_RESERVED_CONTEXTS;
-
-       return 0;
-}
-
-/**
- * Add context.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument pointing to a drm_ctx structure.
- * \return zero on success or a negative number on failure.
- *
- * Get a new handle for the context and copy to userspace.
- */
-int drm_addctx(struct drm_device *dev, void *data,
-              struct drm_file *file_priv)
-{
-       struct drm_ctx_list *ctx_entry;
-       struct drm_ctx *ctx = data;
-
-       ctx->handle = drm_ctxbitmap_next(dev);
-       if (ctx->handle == DRM_KERNEL_CONTEXT) {
-               /* Skip kernel's context and get a new one. */
-               ctx->handle = drm_ctxbitmap_next(dev);
-       }
-       DRM_DEBUG("%d\n", ctx->handle);
-       if (ctx->handle == -1) {
-               DRM_DEBUG("Not enough free contexts.\n");
-               /* Should this return -EBUSY instead? */
-               return -ENOMEM;
-       }
-
-       ctx_entry = kmalloc(sizeof(*ctx_entry), GFP_KERNEL);
-       if (!ctx_entry) {
-               DRM_DEBUG("out of memory\n");
-               return -ENOMEM;
-       }
-
-       INIT_LIST_HEAD(&ctx_entry->head);
-       ctx_entry->handle = ctx->handle;
-       ctx_entry->tag = file_priv;
-
-       mutex_lock(&dev->ctxlist_mutex);
-       list_add(&ctx_entry->head, &dev->ctxlist);
-       ++dev->ctx_count;
-       mutex_unlock(&dev->ctxlist_mutex);
-
-       return 0;
-}
-
-int drm_modctx(struct drm_device *dev, void *data, struct drm_file *file_priv)
-{
-       /* This does nothing */
-       return 0;
-}
-
-/**
- * Get context.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument pointing to a drm_ctx structure.
- * \return zero on success or a negative number on failure.
- */
-int drm_getctx(struct drm_device *dev, void *data, struct drm_file *file_priv)
-{
-       struct drm_ctx *ctx = data;
-
-       /* This is 0, because we don't handle any context flags */
-       ctx->flags = 0;
-
-       return 0;
-}
-
-/**
- * Switch context.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument pointing to a drm_ctx structure.
- * \return zero on success or a negative number on failure.
- *
- * Calls context_switch().
- */
-int drm_switchctx(struct drm_device *dev, void *data,
-                 struct drm_file *file_priv)
-{
-       struct drm_ctx *ctx = data;
-
-       DRM_DEBUG("%d\n", ctx->handle);
-       return drm_context_switch(dev, dev->last_context, ctx->handle);
-}
-
-/**
- * New context.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument pointing to a drm_ctx structure.
- * \return zero on success or a negative number on failure.
- *
- * Calls context_switch_complete().
- */
-int drm_newctx(struct drm_device *dev, void *data,
-              struct drm_file *file_priv)
-{
-       struct drm_ctx *ctx = data;
-
-       DRM_DEBUG("%d\n", ctx->handle);
-       drm_context_switch_complete(dev, file_priv, ctx->handle);
-
-       return 0;
-}
-
-/**
- * Remove context.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument pointing to a drm_ctx structure.
- * \return zero on success or a negative number on failure.
- *
- * If not the special kernel context, calls ctxbitmap_free() to free the specified context.
- */
-int drm_rmctx(struct drm_device *dev, void *data,
-             struct drm_file *file_priv)
-{
-       struct drm_ctx *ctx = data;
-
-       DRM_DEBUG("%d\n", ctx->handle);
-       if (ctx->handle != DRM_KERNEL_CONTEXT) {
-               if (dev->driver->context_dtor)
-                       dev->driver->context_dtor(dev, ctx->handle);
-               drm_ctxbitmap_free(dev, ctx->handle);
-       }
-
-       mutex_lock(&dev->ctxlist_mutex);
-       if (!list_empty(&dev->ctxlist)) {
-               struct drm_ctx_list *pos, *n;
-
-               list_for_each_entry_safe(pos, n, &dev->ctxlist, head) {
-                       if (pos->handle == ctx->handle) {
-                               list_del(&pos->head);
-                               kfree(pos);
-                               --dev->ctx_count;
-                       }
-               }
-       }
-       mutex_unlock(&dev->ctxlist_mutex);
-
-       return 0;
-}
-
-/*@}*/
diff --git a/services4/3rdparty/linux_drm/drm_crtc.c b/services4/3rdparty/linux_drm/drm_crtc.c
deleted file mode 100644 (file)
index 2baa670..0000000
+++ /dev/null
@@ -1,2676 +0,0 @@
-/*
- * Copyright (c) 2006-2008 Intel Corporation
- * Copyright (c) 2007 Dave Airlie <airlied@linux.ie>
- * Copyright (c) 2008 Red Hat Inc.
- *
- * DRM core CRTC related functions
- *
- * Permission to use, copy, modify, distribute, and sell this software and its
- * documentation for any purpose is hereby granted without fee, provided that
- * the above copyright notice appear in all copies and that both that copyright
- * notice and this permission notice appear in supporting documentation, and
- * that the name of the copyright holders not be used in advertising or
- * publicity pertaining to distribution of the software without specific,
- * written prior permission.  The copyright holders make no representations
- * about the suitability of this software for any purpose.  It is provided "as
- * is" without express or implied warranty.
- *
- * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
- * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
- * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
- * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
- * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
- * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
- * OF THIS SOFTWARE.
- *
- * Authors:
- *      Keith Packard
- *     Eric Anholt <eric@anholt.net>
- *      Dave Airlie <airlied@linux.ie>
- *      Jesse Barnes <jesse.barnes@intel.com>
- */
-#include <linux/list.h>
-#include <linux/slab.h>
-#include "drm.h"
-#include "drmP.h"
-#include "drm_crtc.h"
-#include "drm_edid.h"
-
-struct drm_prop_enum_list {
-       int type;
-       char *name;
-};
-
-/* Avoid boilerplate.  I'm tired of typing. */
-#define DRM_ENUM_NAME_FN(fnname, list)                         \
-       char *fnname(int val)                                   \
-       {                                                       \
-               int i;                                          \
-               for (i = 0; i < ARRAY_SIZE(list); i++) {        \
-                       if (list[i].type == val)                \
-                               return list[i].name;            \
-               }                                               \
-               return "(unknown)";                             \
-       }
-
-/*
- * Global properties
- */
-static struct drm_prop_enum_list drm_dpms_enum_list[] =
-{      { DRM_MODE_DPMS_ON, "On" },
-       { DRM_MODE_DPMS_STANDBY, "Standby" },
-       { DRM_MODE_DPMS_SUSPEND, "Suspend" },
-       { DRM_MODE_DPMS_OFF, "Off" }
-};
-
-DRM_ENUM_NAME_FN(drm_get_dpms_name, drm_dpms_enum_list)
-
-/*
- * Optional properties
- */
-static struct drm_prop_enum_list drm_scaling_mode_enum_list[] =
-{
-       { DRM_MODE_SCALE_NONE, "None" },
-       { DRM_MODE_SCALE_FULLSCREEN, "Full" },
-       { DRM_MODE_SCALE_CENTER, "Center" },
-       { DRM_MODE_SCALE_ASPECT, "Full aspect" },
-};
-
-static struct drm_prop_enum_list drm_dithering_mode_enum_list[] =
-{
-       { DRM_MODE_DITHERING_OFF, "Off" },
-       { DRM_MODE_DITHERING_ON, "On" },
-       { DRM_MODE_DITHERING_AUTO, "Automatic" },
-};
-
-/*
- * Non-global properties, but "required" for certain connectors.
- */
-static struct drm_prop_enum_list drm_dvi_i_select_enum_list[] =
-{
-       { DRM_MODE_SUBCONNECTOR_Automatic, "Automatic" }, /* DVI-I and TV-out */
-       { DRM_MODE_SUBCONNECTOR_DVID,      "DVI-D"     }, /* DVI-I  */
-       { DRM_MODE_SUBCONNECTOR_DVIA,      "DVI-A"     }, /* DVI-I  */
-};
-
-DRM_ENUM_NAME_FN(drm_get_dvi_i_select_name, drm_dvi_i_select_enum_list)
-
-static struct drm_prop_enum_list drm_dvi_i_subconnector_enum_list[] =
-{
-       { DRM_MODE_SUBCONNECTOR_Unknown,   "Unknown"   }, /* DVI-I and TV-out */
-       { DRM_MODE_SUBCONNECTOR_DVID,      "DVI-D"     }, /* DVI-I  */
-       { DRM_MODE_SUBCONNECTOR_DVIA,      "DVI-A"     }, /* DVI-I  */
-};
-
-DRM_ENUM_NAME_FN(drm_get_dvi_i_subconnector_name,
-                drm_dvi_i_subconnector_enum_list)
-
-static struct drm_prop_enum_list drm_tv_select_enum_list[] =
-{
-       { DRM_MODE_SUBCONNECTOR_Automatic, "Automatic" }, /* DVI-I and TV-out */
-       { DRM_MODE_SUBCONNECTOR_Composite, "Composite" }, /* TV-out */
-       { DRM_MODE_SUBCONNECTOR_SVIDEO,    "SVIDEO"    }, /* TV-out */
-       { DRM_MODE_SUBCONNECTOR_Component, "Component" }, /* TV-out */
-       { DRM_MODE_SUBCONNECTOR_SCART,     "SCART"     }, /* TV-out */
-};
-
-DRM_ENUM_NAME_FN(drm_get_tv_select_name, drm_tv_select_enum_list)
-
-static struct drm_prop_enum_list drm_tv_subconnector_enum_list[] =
-{
-       { DRM_MODE_SUBCONNECTOR_Unknown,   "Unknown"   }, /* DVI-I and TV-out */
-       { DRM_MODE_SUBCONNECTOR_Composite, "Composite" }, /* TV-out */
-       { DRM_MODE_SUBCONNECTOR_SVIDEO,    "SVIDEO"    }, /* TV-out */
-       { DRM_MODE_SUBCONNECTOR_Component, "Component" }, /* TV-out */
-       { DRM_MODE_SUBCONNECTOR_SCART,     "SCART"     }, /* TV-out */
-};
-
-DRM_ENUM_NAME_FN(drm_get_tv_subconnector_name,
-                drm_tv_subconnector_enum_list)
-
-static struct drm_prop_enum_list drm_dirty_info_enum_list[] = {
-       { DRM_MODE_DIRTY_OFF,      "Off"      },
-       { DRM_MODE_DIRTY_ON,       "On"       },
-       { DRM_MODE_DIRTY_ANNOTATE, "Annotate" },
-};
-
-DRM_ENUM_NAME_FN(drm_get_dirty_info_name,
-                drm_dirty_info_enum_list)
-
-struct drm_conn_prop_enum_list {
-       int type;
-       char *name;
-       int count;
-};
-
-/*
- * Connector and encoder types.
- */
-static struct drm_conn_prop_enum_list drm_connector_enum_list[] =
-{      { DRM_MODE_CONNECTOR_Unknown, "Unknown", 0 },
-       { DRM_MODE_CONNECTOR_VGA, "VGA", 0 },
-       { DRM_MODE_CONNECTOR_DVII, "DVI-I", 0 },
-       { DRM_MODE_CONNECTOR_DVID, "DVI-D", 0 },
-       { DRM_MODE_CONNECTOR_DVIA, "DVI-A", 0 },
-       { DRM_MODE_CONNECTOR_Composite, "Composite", 0 },
-       { DRM_MODE_CONNECTOR_SVIDEO, "SVIDEO", 0 },
-       { DRM_MODE_CONNECTOR_LVDS, "LVDS", 0 },
-       { DRM_MODE_CONNECTOR_Component, "Component", 0 },
-       { DRM_MODE_CONNECTOR_9PinDIN, "DIN", 0 },
-       { DRM_MODE_CONNECTOR_DisplayPort, "DP", 0 },
-       { DRM_MODE_CONNECTOR_HDMIA, "HDMI-A", 0 },
-       { DRM_MODE_CONNECTOR_HDMIB, "HDMI-B", 0 },
-       { DRM_MODE_CONNECTOR_TV, "TV", 0 },
-       { DRM_MODE_CONNECTOR_eDP, "eDP", 0 },
-};
-
-static struct drm_prop_enum_list drm_encoder_enum_list[] =
-{      { DRM_MODE_ENCODER_NONE, "None" },
-       { DRM_MODE_ENCODER_DAC, "DAC" },
-       { DRM_MODE_ENCODER_TMDS, "TMDS" },
-       { DRM_MODE_ENCODER_LVDS, "LVDS" },
-       { DRM_MODE_ENCODER_TVDAC, "TV" },
-};
-
-char *drm_get_encoder_name(struct drm_encoder *encoder)
-{
-       static char buf[32];
-
-       snprintf(buf, 32, "%s-%d",
-                drm_encoder_enum_list[encoder->encoder_type].name,
-                encoder->base.id);
-       return buf;
-}
-EXPORT_SYMBOL(drm_get_encoder_name);
-
-char *drm_get_connector_name(struct drm_connector *connector)
-{
-       static char buf[32];
-
-       snprintf(buf, 32, "%s-%d",
-                drm_connector_enum_list[connector->connector_type].name,
-                connector->connector_type_id);
-       return buf;
-}
-EXPORT_SYMBOL(drm_get_connector_name);
-
-char *drm_get_connector_status_name(enum drm_connector_status status)
-{
-       if (status == connector_status_connected)
-               return "connected";
-       else if (status == connector_status_disconnected)
-               return "disconnected";
-       else
-               return "unknown";
-}
-
-/**
- * drm_mode_object_get - allocate a new identifier
- * @dev: DRM device
- * @ptr: object pointer, used to generate unique ID
- * @type: object type
- *
- * LOCKING:
- *
- * Create a unique identifier based on @ptr in @dev's identifier space.  Used
- * for tracking modes, CRTCs and connectors.
- *
- * RETURNS:
- * New unique (relative to other objects in @dev) integer identifier for the
- * object.
- */
-static int drm_mode_object_get(struct drm_device *dev,
-                              struct drm_mode_object *obj, uint32_t obj_type)
-{
-       int new_id = 0;
-       int ret;
-
-again:
-       if (idr_pre_get(&dev->mode_config.crtc_idr, GFP_KERNEL) == 0) {
-               DRM_ERROR("Ran out memory getting a mode number\n");
-               return -EINVAL;
-       }
-
-       mutex_lock(&dev->mode_config.idr_mutex);
-       ret = idr_get_new_above(&dev->mode_config.crtc_idr, obj, 1, &new_id);
-       mutex_unlock(&dev->mode_config.idr_mutex);
-       if (ret == -EAGAIN)
-               goto again;
-
-       obj->id = new_id;
-       obj->type = obj_type;
-       return 0;
-}
-
-/**
- * drm_mode_object_put - free an identifer
- * @dev: DRM device
- * @id: ID to free
- *
- * LOCKING:
- * Caller must hold DRM mode_config lock.
- *
- * Free @id from @dev's unique identifier pool.
- */
-static void drm_mode_object_put(struct drm_device *dev,
-                               struct drm_mode_object *object)
-{
-       mutex_lock(&dev->mode_config.idr_mutex);
-       idr_remove(&dev->mode_config.crtc_idr, object->id);
-       mutex_unlock(&dev->mode_config.idr_mutex);
-}
-
-struct drm_mode_object *drm_mode_object_find(struct drm_device *dev,
-               uint32_t id, uint32_t type)
-{
-       struct drm_mode_object *obj = NULL;
-
-       mutex_lock(&dev->mode_config.idr_mutex);
-       obj = idr_find(&dev->mode_config.crtc_idr, id);
-       if (!obj || (obj->type != type) || (obj->id != id))
-               obj = NULL;
-       mutex_unlock(&dev->mode_config.idr_mutex);
-
-       return obj;
-}
-EXPORT_SYMBOL(drm_mode_object_find);
-
-/**
- * drm_framebuffer_init - initialize a framebuffer
- * @dev: DRM device
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Allocates an ID for the framebuffer's parent mode object, sets its mode
- * functions & device file and adds it to the master fd list.
- *
- * RETURNS:
- * Zero on success, error code on failure.
- */
-int drm_framebuffer_init(struct drm_device *dev, struct drm_framebuffer *fb,
-                        const struct drm_framebuffer_funcs *funcs)
-{
-       int ret;
-
-       ret = drm_mode_object_get(dev, &fb->base, DRM_MODE_OBJECT_FB);
-       if (ret) {
-               return ret;
-       }
-
-       fb->dev = dev;
-       fb->funcs = funcs;
-       dev->mode_config.num_fb++;
-       list_add(&fb->head, &dev->mode_config.fb_list);
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_framebuffer_init);
-
-/**
- * drm_framebuffer_cleanup - remove a framebuffer object
- * @fb: framebuffer to remove
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Scans all the CRTCs in @dev's mode_config.  If they're using @fb, removes
- * it, setting it to NULL.
- */
-void drm_framebuffer_cleanup(struct drm_framebuffer *fb)
-{
-       struct drm_device *dev = fb->dev;
-       struct drm_crtc *crtc;
-       struct drm_mode_set set;
-       int ret;
-
-       /* remove from any CRTC */
-       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
-               if (crtc->fb == fb) {
-                       /* should turn off the crtc */
-                       memset(&set, 0, sizeof(struct drm_mode_set));
-                       set.crtc = crtc;
-                       set.fb = NULL;
-                       ret = crtc->funcs->set_config(&set);
-                       if (ret)
-                               DRM_ERROR("failed to reset crtc %p when fb was deleted\n", crtc);
-               }
-       }
-
-       drm_mode_object_put(dev, &fb->base);
-       list_del(&fb->head);
-       dev->mode_config.num_fb--;
-}
-EXPORT_SYMBOL(drm_framebuffer_cleanup);
-
-/**
- * drm_crtc_init - Initialise a new CRTC object
- * @dev: DRM device
- * @crtc: CRTC object to init
- * @funcs: callbacks for the new CRTC
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Inits a new object created as base part of an driver crtc object.
- */
-void drm_crtc_init(struct drm_device *dev, struct drm_crtc *crtc,
-                  const struct drm_crtc_funcs *funcs)
-{
-       crtc->dev = dev;
-       crtc->funcs = funcs;
-
-       mutex_lock(&dev->mode_config.mutex);
-       drm_mode_object_get(dev, &crtc->base, DRM_MODE_OBJECT_CRTC);
-
-       list_add_tail(&crtc->head, &dev->mode_config.crtc_list);
-       dev->mode_config.num_crtc++;
-       mutex_unlock(&dev->mode_config.mutex);
-}
-EXPORT_SYMBOL(drm_crtc_init);
-
-/**
- * drm_crtc_cleanup - Cleans up the core crtc usage.
- * @crtc: CRTC to cleanup
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Cleanup @crtc. Removes from drm modesetting space
- * does NOT free object, caller does that.
- */
-void drm_crtc_cleanup(struct drm_crtc *crtc)
-{
-       struct drm_device *dev = crtc->dev;
-
-       if (crtc->gamma_store) {
-               kfree(crtc->gamma_store);
-               crtc->gamma_store = NULL;
-       }
-
-       drm_mode_object_put(dev, &crtc->base);
-       list_del(&crtc->head);
-       dev->mode_config.num_crtc--;
-}
-EXPORT_SYMBOL(drm_crtc_cleanup);
-
-/**
- * drm_mode_probed_add - add a mode to a connector's probed mode list
- * @connector: connector the new mode
- * @mode: mode data
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Add @mode to @connector's mode list for later use.
- */
-void drm_mode_probed_add(struct drm_connector *connector,
-                        struct drm_display_mode *mode)
-{
-       list_add(&mode->head, &connector->probed_modes);
-}
-EXPORT_SYMBOL(drm_mode_probed_add);
-
-/**
- * drm_mode_remove - remove and free a mode
- * @connector: connector list to modify
- * @mode: mode to remove
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Remove @mode from @connector's mode list, then free it.
- */
-void drm_mode_remove(struct drm_connector *connector,
-                    struct drm_display_mode *mode)
-{
-       list_del(&mode->head);
-       kfree(mode);
-}
-EXPORT_SYMBOL(drm_mode_remove);
-
-/**
- * drm_connector_init - Init a preallocated connector
- * @dev: DRM device
- * @connector: the connector to init
- * @funcs: callbacks for this connector
- * @name: user visible name of the connector
- *
- * LOCKING:
- * Caller must hold @dev's mode_config lock.
- *
- * Initialises a preallocated connector. Connectors should be
- * subclassed as part of driver connector objects.
- */
-void drm_connector_init(struct drm_device *dev,
-                    struct drm_connector *connector,
-                    const struct drm_connector_funcs *funcs,
-                    int connector_type)
-{
-       mutex_lock(&dev->mode_config.mutex);
-
-       connector->dev = dev;
-       connector->funcs = funcs;
-       drm_mode_object_get(dev, &connector->base, DRM_MODE_OBJECT_CONNECTOR);
-       connector->connector_type = connector_type;
-       connector->connector_type_id =
-               ++drm_connector_enum_list[connector_type].count; /* TODO */
-       INIT_LIST_HEAD(&connector->user_modes);
-       INIT_LIST_HEAD(&connector->probed_modes);
-       INIT_LIST_HEAD(&connector->modes);
-       connector->edid_blob_ptr = NULL;
-
-       list_add_tail(&connector->head, &dev->mode_config.connector_list);
-       dev->mode_config.num_connector++;
-
-       drm_connector_attach_property(connector,
-                                     dev->mode_config.edid_property, 0);
-
-       drm_connector_attach_property(connector,
-                                     dev->mode_config.dpms_property, 0);
-
-       mutex_unlock(&dev->mode_config.mutex);
-}
-EXPORT_SYMBOL(drm_connector_init);
-
-/**
- * drm_connector_cleanup - cleans up an initialised connector
- * @connector: connector to cleanup
- *
- * LOCKING:
- * Caller must hold @dev's mode_config lock.
- *
- * Cleans up the connector but doesn't free the object.
- */
-void drm_connector_cleanup(struct drm_connector *connector)
-{
-       struct drm_device *dev = connector->dev;
-       struct drm_display_mode *mode, *t;
-
-       list_for_each_entry_safe(mode, t, &connector->probed_modes, head)
-               drm_mode_remove(connector, mode);
-
-       list_for_each_entry_safe(mode, t, &connector->modes, head)
-               drm_mode_remove(connector, mode);
-
-       list_for_each_entry_safe(mode, t, &connector->user_modes, head)
-               drm_mode_remove(connector, mode);
-
-       mutex_lock(&dev->mode_config.mutex);
-       drm_mode_object_put(dev, &connector->base);
-       list_del(&connector->head);
-       mutex_unlock(&dev->mode_config.mutex);
-}
-EXPORT_SYMBOL(drm_connector_cleanup);
-
-void drm_encoder_init(struct drm_device *dev,
-                     struct drm_encoder *encoder,
-                     const struct drm_encoder_funcs *funcs,
-                     int encoder_type)
-{
-       mutex_lock(&dev->mode_config.mutex);
-
-       encoder->dev = dev;
-
-       drm_mode_object_get(dev, &encoder->base, DRM_MODE_OBJECT_ENCODER);
-       encoder->encoder_type = encoder_type;
-       encoder->funcs = funcs;
-
-       list_add_tail(&encoder->head, &dev->mode_config.encoder_list);
-       dev->mode_config.num_encoder++;
-
-       mutex_unlock(&dev->mode_config.mutex);
-}
-EXPORT_SYMBOL(drm_encoder_init);
-
-void drm_encoder_cleanup(struct drm_encoder *encoder)
-{
-       struct drm_device *dev = encoder->dev;
-       mutex_lock(&dev->mode_config.mutex);
-       drm_mode_object_put(dev, &encoder->base);
-       list_del(&encoder->head);
-       mutex_unlock(&dev->mode_config.mutex);
-}
-EXPORT_SYMBOL(drm_encoder_cleanup);
-
-/**
- * drm_mode_create - create a new display mode
- * @dev: DRM device
- *
- * LOCKING:
- * Caller must hold DRM mode_config lock.
- *
- * Create a new drm_display_mode, give it an ID, and return it.
- *
- * RETURNS:
- * Pointer to new mode on success, NULL on error.
- */
-struct drm_display_mode *drm_mode_create(struct drm_device *dev)
-{
-       struct drm_display_mode *nmode;
-
-       nmode = kzalloc(sizeof(struct drm_display_mode), GFP_KERNEL);
-       if (!nmode)
-               return NULL;
-
-       drm_mode_object_get(dev, &nmode->base, DRM_MODE_OBJECT_MODE);
-       return nmode;
-}
-EXPORT_SYMBOL(drm_mode_create);
-
-/**
- * drm_mode_destroy - remove a mode
- * @dev: DRM device
- * @mode: mode to remove
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Free @mode's unique identifier, then free it.
- */
-void drm_mode_destroy(struct drm_device *dev, struct drm_display_mode *mode)
-{
-       drm_mode_object_put(dev, &mode->base);
-
-       kfree(mode);
-}
-EXPORT_SYMBOL(drm_mode_destroy);
-
-static int drm_mode_create_standard_connector_properties(struct drm_device *dev)
-{
-       struct drm_property *edid;
-       struct drm_property *dpms;
-       int i;
-
-       /*
-        * Standard properties (apply to all connectors)
-        */
-       edid = drm_property_create(dev, DRM_MODE_PROP_BLOB |
-                                  DRM_MODE_PROP_IMMUTABLE,
-                                  "EDID", 0);
-       dev->mode_config.edid_property = edid;
-
-       dpms = drm_property_create(dev, DRM_MODE_PROP_ENUM,
-                                  "DPMS", ARRAY_SIZE(drm_dpms_enum_list));
-       for (i = 0; i < ARRAY_SIZE(drm_dpms_enum_list); i++)
-               drm_property_add_enum(dpms, i, drm_dpms_enum_list[i].type,
-                                     drm_dpms_enum_list[i].name);
-       dev->mode_config.dpms_property = dpms;
-
-       return 0;
-}
-
-/**
- * drm_mode_create_dvi_i_properties - create DVI-I specific connector properties
- * @dev: DRM device
- *
- * Called by a driver the first time a DVI-I connector is made.
- */
-int drm_mode_create_dvi_i_properties(struct drm_device *dev)
-{
-       struct drm_property *dvi_i_selector;
-       struct drm_property *dvi_i_subconnector;
-       int i;
-
-       if (dev->mode_config.dvi_i_select_subconnector_property)
-               return 0;
-
-       dvi_i_selector =
-               drm_property_create(dev, DRM_MODE_PROP_ENUM,
-                                   "select subconnector",
-                                   ARRAY_SIZE(drm_dvi_i_select_enum_list));
-       for (i = 0; i < ARRAY_SIZE(drm_dvi_i_select_enum_list); i++)
-               drm_property_add_enum(dvi_i_selector, i,
-                                     drm_dvi_i_select_enum_list[i].type,
-                                     drm_dvi_i_select_enum_list[i].name);
-       dev->mode_config.dvi_i_select_subconnector_property = dvi_i_selector;
-
-       dvi_i_subconnector =
-               drm_property_create(dev, DRM_MODE_PROP_ENUM |
-                                   DRM_MODE_PROP_IMMUTABLE,
-                                   "subconnector",
-                                   ARRAY_SIZE(drm_dvi_i_subconnector_enum_list));
-       for (i = 0; i < ARRAY_SIZE(drm_dvi_i_subconnector_enum_list); i++)
-               drm_property_add_enum(dvi_i_subconnector, i,
-                                     drm_dvi_i_subconnector_enum_list[i].type,
-                                     drm_dvi_i_subconnector_enum_list[i].name);
-       dev->mode_config.dvi_i_subconnector_property = dvi_i_subconnector;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_mode_create_dvi_i_properties);
-
-/**
- * drm_create_tv_properties - create TV specific connector properties
- * @dev: DRM device
- * @num_modes: number of different TV formats (modes) supported
- * @modes: array of pointers to strings containing name of each format
- *
- * Called by a driver's TV initialization routine, this function creates
- * the TV specific connector properties for a given device.  Caller is
- * responsible for allocating a list of format names and passing them to
- * this routine.
- */
-int drm_mode_create_tv_properties(struct drm_device *dev, int num_modes,
-                                 char *modes[])
-{
-       struct drm_property *tv_selector;
-       struct drm_property *tv_subconnector;
-       int i;
-
-       if (dev->mode_config.tv_select_subconnector_property)
-               return 0;
-
-       /*
-        * Basic connector properties
-        */
-       tv_selector = drm_property_create(dev, DRM_MODE_PROP_ENUM,
-                                         "select subconnector",
-                                         ARRAY_SIZE(drm_tv_select_enum_list));
-       for (i = 0; i < ARRAY_SIZE(drm_tv_select_enum_list); i++)
-               drm_property_add_enum(tv_selector, i,
-                                     drm_tv_select_enum_list[i].type,
-                                     drm_tv_select_enum_list[i].name);
-       dev->mode_config.tv_select_subconnector_property = tv_selector;
-
-       tv_subconnector =
-               drm_property_create(dev, DRM_MODE_PROP_ENUM |
-                                   DRM_MODE_PROP_IMMUTABLE, "subconnector",
-                                   ARRAY_SIZE(drm_tv_subconnector_enum_list));
-       for (i = 0; i < ARRAY_SIZE(drm_tv_subconnector_enum_list); i++)
-               drm_property_add_enum(tv_subconnector, i,
-                                     drm_tv_subconnector_enum_list[i].type,
-                                     drm_tv_subconnector_enum_list[i].name);
-       dev->mode_config.tv_subconnector_property = tv_subconnector;
-
-       /*
-        * Other, TV specific properties: margins & TV modes.
-        */
-       dev->mode_config.tv_left_margin_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "left margin", 2);
-       dev->mode_config.tv_left_margin_property->values[0] = 0;
-       dev->mode_config.tv_left_margin_property->values[1] = 100;
-
-       dev->mode_config.tv_right_margin_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "right margin", 2);
-       dev->mode_config.tv_right_margin_property->values[0] = 0;
-       dev->mode_config.tv_right_margin_property->values[1] = 100;
-
-       dev->mode_config.tv_top_margin_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "top margin", 2);
-       dev->mode_config.tv_top_margin_property->values[0] = 0;
-       dev->mode_config.tv_top_margin_property->values[1] = 100;
-
-       dev->mode_config.tv_bottom_margin_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "bottom margin", 2);
-       dev->mode_config.tv_bottom_margin_property->values[0] = 0;
-       dev->mode_config.tv_bottom_margin_property->values[1] = 100;
-
-       dev->mode_config.tv_mode_property =
-               drm_property_create(dev, DRM_MODE_PROP_ENUM,
-                                   "mode", num_modes);
-       for (i = 0; i < num_modes; i++)
-               drm_property_add_enum(dev->mode_config.tv_mode_property, i,
-                                     i, modes[i]);
-
-       dev->mode_config.tv_brightness_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "brightness", 2);
-       dev->mode_config.tv_brightness_property->values[0] = 0;
-       dev->mode_config.tv_brightness_property->values[1] = 100;
-
-       dev->mode_config.tv_contrast_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "contrast", 2);
-       dev->mode_config.tv_contrast_property->values[0] = 0;
-       dev->mode_config.tv_contrast_property->values[1] = 100;
-
-       dev->mode_config.tv_flicker_reduction_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "flicker reduction", 2);
-       dev->mode_config.tv_flicker_reduction_property->values[0] = 0;
-       dev->mode_config.tv_flicker_reduction_property->values[1] = 100;
-
-       dev->mode_config.tv_overscan_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "overscan", 2);
-       dev->mode_config.tv_overscan_property->values[0] = 0;
-       dev->mode_config.tv_overscan_property->values[1] = 100;
-
-       dev->mode_config.tv_saturation_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "saturation", 2);
-       dev->mode_config.tv_saturation_property->values[0] = 0;
-       dev->mode_config.tv_saturation_property->values[1] = 100;
-
-       dev->mode_config.tv_hue_property =
-               drm_property_create(dev, DRM_MODE_PROP_RANGE,
-                                   "hue", 2);
-       dev->mode_config.tv_hue_property->values[0] = 0;
-       dev->mode_config.tv_hue_property->values[1] = 100;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_mode_create_tv_properties);
-
-/**
- * drm_mode_create_scaling_mode_property - create scaling mode property
- * @dev: DRM device
- *
- * Called by a driver the first time it's needed, must be attached to desired
- * connectors.
- */
-int drm_mode_create_scaling_mode_property(struct drm_device *dev)
-{
-       struct drm_property *scaling_mode;
-       int i;
-
-       if (dev->mode_config.scaling_mode_property)
-               return 0;
-
-       scaling_mode =
-               drm_property_create(dev, DRM_MODE_PROP_ENUM, "scaling mode",
-                                   ARRAY_SIZE(drm_scaling_mode_enum_list));
-       for (i = 0; i < ARRAY_SIZE(drm_scaling_mode_enum_list); i++)
-               drm_property_add_enum(scaling_mode, i,
-                                     drm_scaling_mode_enum_list[i].type,
-                                     drm_scaling_mode_enum_list[i].name);
-
-       dev->mode_config.scaling_mode_property = scaling_mode;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_mode_create_scaling_mode_property);
-
-/**
- * drm_mode_create_dithering_property - create dithering property
- * @dev: DRM device
- *
- * Called by a driver the first time it's needed, must be attached to desired
- * connectors.
- */
-int drm_mode_create_dithering_property(struct drm_device *dev)
-{
-       struct drm_property *dithering_mode;
-       int i;
-
-       if (dev->mode_config.dithering_mode_property)
-               return 0;
-
-       dithering_mode =
-               drm_property_create(dev, DRM_MODE_PROP_ENUM, "dithering",
-                                   ARRAY_SIZE(drm_dithering_mode_enum_list));
-       for (i = 0; i < ARRAY_SIZE(drm_dithering_mode_enum_list); i++)
-               drm_property_add_enum(dithering_mode, i,
-                                     drm_dithering_mode_enum_list[i].type,
-                                     drm_dithering_mode_enum_list[i].name);
-       dev->mode_config.dithering_mode_property = dithering_mode;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_mode_create_dithering_property);
-
-/**
- * drm_mode_create_dirty_property - create dirty property
- * @dev: DRM device
- *
- * Called by a driver the first time it's needed, must be attached to desired
- * connectors.
- */
-int drm_mode_create_dirty_info_property(struct drm_device *dev)
-{
-       struct drm_property *dirty_info;
-       int i;
-
-       if (dev->mode_config.dirty_info_property)
-               return 0;
-
-       dirty_info =
-               drm_property_create(dev, DRM_MODE_PROP_ENUM |
-                                   DRM_MODE_PROP_IMMUTABLE,
-                                   "dirty",
-                                   ARRAY_SIZE(drm_dirty_info_enum_list));
-       for (i = 0; i < ARRAY_SIZE(drm_dirty_info_enum_list); i++)
-               drm_property_add_enum(dirty_info, i,
-                                     drm_dirty_info_enum_list[i].type,
-                                     drm_dirty_info_enum_list[i].name);
-       dev->mode_config.dirty_info_property = dirty_info;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_mode_create_dirty_info_property);
-
-/**
- * drm_mode_config_init - initialize DRM mode_configuration structure
- * @dev: DRM device
- *
- * LOCKING:
- * None, should happen single threaded at init time.
- *
- * Initialize @dev's mode_config structure, used for tracking the graphics
- * configuration of @dev.
- */
-void drm_mode_config_init(struct drm_device *dev)
-{
-       mutex_init(&dev->mode_config.mutex);
-       mutex_init(&dev->mode_config.idr_mutex);
-       INIT_LIST_HEAD(&dev->mode_config.fb_list);
-       INIT_LIST_HEAD(&dev->mode_config.crtc_list);
-       INIT_LIST_HEAD(&dev->mode_config.connector_list);
-       INIT_LIST_HEAD(&dev->mode_config.encoder_list);
-       INIT_LIST_HEAD(&dev->mode_config.property_list);
-       INIT_LIST_HEAD(&dev->mode_config.property_blob_list);
-       idr_init(&dev->mode_config.crtc_idr);
-
-       mutex_lock(&dev->mode_config.mutex);
-       drm_mode_create_standard_connector_properties(dev);
-       mutex_unlock(&dev->mode_config.mutex);
-
-       /* Just to be sure */
-       dev->mode_config.num_fb = 0;
-       dev->mode_config.num_connector = 0;
-       dev->mode_config.num_crtc = 0;
-       dev->mode_config.num_encoder = 0;
-}
-EXPORT_SYMBOL(drm_mode_config_init);
-
-int drm_mode_group_init(struct drm_device *dev, struct drm_mode_group *group)
-{
-       uint32_t total_objects = 0;
-
-       total_objects += dev->mode_config.num_crtc;
-       total_objects += dev->mode_config.num_connector;
-       total_objects += dev->mode_config.num_encoder;
-
-       if (total_objects == 0)
-               return -EINVAL;
-
-       group->id_list = kzalloc(total_objects * sizeof(uint32_t), GFP_KERNEL);
-       if (!group->id_list)
-               return -ENOMEM;
-
-       group->num_crtcs = 0;
-       group->num_connectors = 0;
-       group->num_encoders = 0;
-       return 0;
-}
-
-int drm_mode_group_init_legacy_group(struct drm_device *dev,
-                                    struct drm_mode_group *group)
-{
-       struct drm_crtc *crtc;
-       struct drm_encoder *encoder;
-       struct drm_connector *connector;
-       int ret;
-
-       if ((ret = drm_mode_group_init(dev, group)))
-               return ret;
-
-       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
-               group->id_list[group->num_crtcs++] = crtc->base.id;
-
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head)
-               group->id_list[group->num_crtcs + group->num_encoders++] =
-               encoder->base.id;
-
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head)
-               group->id_list[group->num_crtcs + group->num_encoders +
-                              group->num_connectors++] = connector->base.id;
-
-       return 0;
-}
-
-/**
- * drm_mode_config_cleanup - free up DRM mode_config info
- * @dev: DRM device
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Free up all the connectors and CRTCs associated with this DRM device, then
- * free up the framebuffers and associated buffer objects.
- *
- * FIXME: cleanup any dangling user buffer objects too
- */
-void drm_mode_config_cleanup(struct drm_device *dev)
-{
-       struct drm_connector *connector, *ot;
-       struct drm_crtc *crtc, *ct;
-       struct drm_encoder *encoder, *enct;
-       struct drm_framebuffer *fb, *fbt;
-       struct drm_property *property, *pt;
-
-       list_for_each_entry_safe(encoder, enct, &dev->mode_config.encoder_list,
-                                head) {
-               encoder->funcs->destroy(encoder);
-       }
-
-       list_for_each_entry_safe(connector, ot,
-                                &dev->mode_config.connector_list, head) {
-               connector->funcs->destroy(connector);
-       }
-
-       list_for_each_entry_safe(property, pt, &dev->mode_config.property_list,
-                                head) {
-               drm_property_destroy(dev, property);
-       }
-
-       list_for_each_entry_safe(fb, fbt, &dev->mode_config.fb_list, head) {
-               fb->funcs->destroy(fb);
-       }
-
-       list_for_each_entry_safe(crtc, ct, &dev->mode_config.crtc_list, head) {
-               crtc->funcs->destroy(crtc);
-       }
-
-}
-EXPORT_SYMBOL(drm_mode_config_cleanup);
-
-/**
- * drm_crtc_convert_to_umode - convert a drm_display_mode into a modeinfo
- * @out: drm_mode_modeinfo struct to return to the user
- * @in: drm_display_mode to use
- *
- * LOCKING:
- * None.
- *
- * Convert a drm_display_mode into a drm_mode_modeinfo structure to return to
- * the user.
- */
-void drm_crtc_convert_to_umode(struct drm_mode_modeinfo *out,
-                              struct drm_display_mode *in)
-{
-       out->clock = in->clock;
-       out->hdisplay = in->hdisplay;
-       out->hsync_start = in->hsync_start;
-       out->hsync_end = in->hsync_end;
-       out->htotal = in->htotal;
-       out->hskew = in->hskew;
-       out->vdisplay = in->vdisplay;
-       out->vsync_start = in->vsync_start;
-       out->vsync_end = in->vsync_end;
-       out->vtotal = in->vtotal;
-       out->vscan = in->vscan;
-       out->vrefresh = in->vrefresh;
-       out->flags = in->flags;
-       out->type = in->type;
-       strncpy(out->name, in->name, DRM_DISPLAY_MODE_LEN);
-       out->name[DRM_DISPLAY_MODE_LEN-1] = 0;
-}
-
-/**
- * drm_crtc_convert_to_umode - convert a modeinfo into a drm_display_mode
- * @out: drm_display_mode to return to the user
- * @in: drm_mode_modeinfo to use
- *
- * LOCKING:
- * None.
- *
- * Convert a drm_mode_modeinfo into a drm_display_mode structure to return to
- * the caller.
- */
-void drm_crtc_convert_umode(struct drm_display_mode *out,
-                           struct drm_mode_modeinfo *in)
-{
-       out->clock = in->clock;
-       out->hdisplay = in->hdisplay;
-       out->hsync_start = in->hsync_start;
-       out->hsync_end = in->hsync_end;
-       out->htotal = in->htotal;
-       out->hskew = in->hskew;
-       out->vdisplay = in->vdisplay;
-       out->vsync_start = in->vsync_start;
-       out->vsync_end = in->vsync_end;
-       out->vtotal = in->vtotal;
-       out->vscan = in->vscan;
-       out->vrefresh = in->vrefresh;
-       out->flags = in->flags;
-       out->type = in->type;
-       strncpy(out->name, in->name, DRM_DISPLAY_MODE_LEN);
-       out->name[DRM_DISPLAY_MODE_LEN-1] = 0;
-}
-
-/**
- * drm_mode_getresources - get graphics configuration
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * LOCKING:
- * Takes mode config lock.
- *
- * Construct a set of configuration description structures and return
- * them to the user, including CRTC, connector and framebuffer configuration.
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_getresources(struct drm_device *dev, void *data,
-                         struct drm_file *file_priv)
-{
-       struct drm_mode_card_res *card_res = data;
-       struct list_head *lh;
-       struct drm_framebuffer *fb;
-       struct drm_connector *connector;
-       struct drm_crtc *crtc;
-       struct drm_encoder *encoder;
-       int ret = 0;
-       int connector_count = 0;
-       int crtc_count = 0;
-       int fb_count = 0;
-       int encoder_count = 0;
-       int copied = 0, i;
-       uint32_t __user *fb_id;
-       uint32_t __user *crtc_id;
-       uint32_t __user *connector_id;
-       uint32_t __user *encoder_id;
-       struct drm_mode_group *mode_group;
-
-       mutex_lock(&dev->mode_config.mutex);
-
-       /*
-        * For the non-control nodes we need to limit the list of resources
-        * by IDs in the group list for this node
-        */
-       list_for_each(lh, &file_priv->fbs)
-               fb_count++;
-
-       mode_group = &file_priv->master->minor->mode_group;
-       if (file_priv->master->minor->type == DRM_MINOR_CONTROL) {
-
-               list_for_each(lh, &dev->mode_config.crtc_list)
-                       crtc_count++;
-
-               list_for_each(lh, &dev->mode_config.connector_list)
-                       connector_count++;
-
-               list_for_each(lh, &dev->mode_config.encoder_list)
-                       encoder_count++;
-       } else {
-
-               crtc_count = mode_group->num_crtcs;
-               connector_count = mode_group->num_connectors;
-               encoder_count = mode_group->num_encoders;
-       }
-
-       card_res->max_height = dev->mode_config.max_height;
-       card_res->min_height = dev->mode_config.min_height;
-       card_res->max_width = dev->mode_config.max_width;
-       card_res->min_width = dev->mode_config.min_width;
-
-       /* handle this in 4 parts */
-       /* FBs */
-       if (card_res->count_fbs >= fb_count) {
-               copied = 0;
-               fb_id = (uint32_t __user *)(unsigned long)card_res->fb_id_ptr;
-               list_for_each_entry(fb, &file_priv->fbs, head) {
-                       if (put_user(fb->base.id, fb_id + copied)) {
-                               ret = -EFAULT;
-                               goto out;
-                       }
-                       copied++;
-               }
-       }
-       card_res->count_fbs = fb_count;
-
-       /* CRTCs */
-       if (card_res->count_crtcs >= crtc_count) {
-               copied = 0;
-               crtc_id = (uint32_t __user *)(unsigned long)card_res->crtc_id_ptr;
-               if (file_priv->master->minor->type == DRM_MINOR_CONTROL) {
-                       list_for_each_entry(crtc, &dev->mode_config.crtc_list,
-                                           head) {
-                               DRM_DEBUG_KMS("[CRTC:%d]\n", crtc->base.id);
-                               if (put_user(crtc->base.id, crtc_id + copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-                               copied++;
-                       }
-               } else {
-                       for (i = 0; i < mode_group->num_crtcs; i++) {
-                               if (put_user(mode_group->id_list[i],
-                                            crtc_id + copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-                               copied++;
-                       }
-               }
-       }
-       card_res->count_crtcs = crtc_count;
-
-       /* Encoders */
-       if (card_res->count_encoders >= encoder_count) {
-               copied = 0;
-               encoder_id = (uint32_t __user *)(unsigned long)card_res->encoder_id_ptr;
-               if (file_priv->master->minor->type == DRM_MINOR_CONTROL) {
-                       list_for_each_entry(encoder,
-                                           &dev->mode_config.encoder_list,
-                                           head) {
-                               DRM_DEBUG_KMS("[ENCODER:%d:%s]\n", encoder->base.id,
-                                               drm_get_encoder_name(encoder));
-                               if (put_user(encoder->base.id, encoder_id +
-                                            copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-                               copied++;
-                       }
-               } else {
-                       for (i = mode_group->num_crtcs; i < mode_group->num_crtcs + mode_group->num_encoders; i++) {
-                               if (put_user(mode_group->id_list[i],
-                                            encoder_id + copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-                               copied++;
-                       }
-
-               }
-       }
-       card_res->count_encoders = encoder_count;
-
-       /* Connectors */
-       if (card_res->count_connectors >= connector_count) {
-               copied = 0;
-               connector_id = (uint32_t __user *)(unsigned long)card_res->connector_id_ptr;
-               if (file_priv->master->minor->type == DRM_MINOR_CONTROL) {
-                       list_for_each_entry(connector,
-                                           &dev->mode_config.connector_list,
-                                           head) {
-                               DRM_DEBUG_KMS("[CONNECTOR:%d:%s]\n",
-                                       connector->base.id,
-                                       drm_get_connector_name(connector));
-                               if (put_user(connector->base.id,
-                                            connector_id + copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-                               copied++;
-                       }
-               } else {
-                       int start = mode_group->num_crtcs +
-                               mode_group->num_encoders;
-                       for (i = start; i < start + mode_group->num_connectors; i++) {
-                               if (put_user(mode_group->id_list[i],
-                                            connector_id + copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-                               copied++;
-                       }
-               }
-       }
-       card_res->count_connectors = connector_count;
-
-       DRM_DEBUG_KMS("CRTC[%d] CONNECTORS[%d] ENCODERS[%d]\n", card_res->count_crtcs,
-                 card_res->count_connectors, card_res->count_encoders);
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-/**
- * drm_mode_getcrtc - get CRTC configuration
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * LOCKING:
- * Caller? (FIXME)
- *
- * Construct a CRTC configuration structure to return to the user.
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_getcrtc(struct drm_device *dev,
-                    void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_crtc *crtc_resp = data;
-       struct drm_crtc *crtc;
-       struct drm_mode_object *obj;
-       int ret = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-
-       obj = drm_mode_object_find(dev, crtc_resp->crtc_id,
-                                  DRM_MODE_OBJECT_CRTC);
-       if (!obj) {
-               ret = -EINVAL;
-               goto out;
-       }
-       crtc = obj_to_crtc(obj);
-
-       crtc_resp->x = crtc->x;
-       crtc_resp->y = crtc->y;
-       crtc_resp->gamma_size = crtc->gamma_size;
-       if (crtc->fb)
-               crtc_resp->fb_id = crtc->fb->base.id;
-       else
-               crtc_resp->fb_id = 0;
-
-       if (crtc->enabled) {
-
-               drm_crtc_convert_to_umode(&crtc_resp->mode, &crtc->mode);
-               crtc_resp->mode_valid = 1;
-
-       } else {
-               crtc_resp->mode_valid = 0;
-       }
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-/**
- * drm_mode_getconnector - get connector configuration
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * LOCKING:
- * Caller? (FIXME)
- *
- * Construct a connector configuration structure to return to the user.
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_getconnector(struct drm_device *dev, void *data,
-                         struct drm_file *file_priv)
-{
-       struct drm_mode_get_connector *out_resp = data;
-       struct drm_mode_object *obj;
-       struct drm_connector *connector;
-       struct drm_display_mode *mode;
-       int mode_count = 0;
-       int props_count = 0;
-       int encoders_count = 0;
-       int ret = 0;
-       int copied = 0;
-       int i;
-       struct drm_mode_modeinfo u_mode;
-       struct drm_mode_modeinfo __user *mode_ptr;
-       uint32_t __user *prop_ptr;
-       uint64_t __user *prop_values;
-       uint32_t __user *encoder_ptr;
-
-       memset(&u_mode, 0, sizeof(struct drm_mode_modeinfo));
-
-       DRM_DEBUG_KMS("[CONNECTOR:%d:?]\n", out_resp->connector_id);
-
-       mutex_lock(&dev->mode_config.mutex);
-
-       obj = drm_mode_object_find(dev, out_resp->connector_id,
-                                  DRM_MODE_OBJECT_CONNECTOR);
-       if (!obj) {
-               ret = -EINVAL;
-               goto out;
-       }
-       connector = obj_to_connector(obj);
-
-       for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
-               if (connector->property_ids[i] != 0) {
-                       props_count++;
-               }
-       }
-
-       for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
-               if (connector->encoder_ids[i] != 0) {
-                       encoders_count++;
-               }
-       }
-
-       if (out_resp->count_modes == 0) {
-               connector->funcs->fill_modes(connector,
-                                            dev->mode_config.max_width,
-                                            dev->mode_config.max_height);
-       }
-
-       /* delayed so we get modes regardless of pre-fill_modes state */
-       list_for_each_entry(mode, &connector->modes, head)
-               mode_count++;
-
-       out_resp->connector_id = connector->base.id;
-       out_resp->connector_type = connector->connector_type;
-       out_resp->connector_type_id = connector->connector_type_id;
-       out_resp->mm_width = connector->display_info.width_mm;
-       out_resp->mm_height = connector->display_info.height_mm;
-       out_resp->subpixel = connector->display_info.subpixel_order;
-       out_resp->connection = connector->status;
-       if (connector->encoder)
-               out_resp->encoder_id = connector->encoder->base.id;
-       else
-               out_resp->encoder_id = 0;
-
-       /*
-        * This ioctl is called twice, once to determine how much space is
-        * needed, and the 2nd time to fill it.
-        */
-       if ((out_resp->count_modes >= mode_count) && mode_count) {
-               copied = 0;
-               mode_ptr = (struct drm_mode_modeinfo *)(unsigned long)out_resp->modes_ptr;
-               list_for_each_entry(mode, &connector->modes, head) {
-                       drm_crtc_convert_to_umode(&u_mode, mode);
-                       if (copy_to_user(mode_ptr + copied,
-                                        &u_mode, sizeof(u_mode))) {
-                               ret = -EFAULT;
-                               goto out;
-                       }
-                       copied++;
-               }
-       }
-       out_resp->count_modes = mode_count;
-
-       if ((out_resp->count_props >= props_count) && props_count) {
-               copied = 0;
-               prop_ptr = (uint32_t *)(unsigned long)(out_resp->props_ptr);
-               prop_values = (uint64_t *)(unsigned long)(out_resp->prop_values_ptr);
-               for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
-                       if (connector->property_ids[i] != 0) {
-                               if (put_user(connector->property_ids[i],
-                                            prop_ptr + copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-
-                               if (put_user(connector->property_values[i],
-                                            prop_values + copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-                               copied++;
-                       }
-               }
-       }
-       out_resp->count_props = props_count;
-
-       if ((out_resp->count_encoders >= encoders_count) && encoders_count) {
-               copied = 0;
-               encoder_ptr = (uint32_t *)(unsigned long)(out_resp->encoders_ptr);
-               for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
-                       if (connector->encoder_ids[i] != 0) {
-                               if (put_user(connector->encoder_ids[i],
-                                            encoder_ptr + copied)) {
-                                       ret = -EFAULT;
-                                       goto out;
-                               }
-                               copied++;
-                       }
-               }
-       }
-       out_resp->count_encoders = encoders_count;
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-int drm_mode_getencoder(struct drm_device *dev, void *data,
-                       struct drm_file *file_priv)
-{
-       struct drm_mode_get_encoder *enc_resp = data;
-       struct drm_mode_object *obj;
-       struct drm_encoder *encoder;
-       int ret = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, enc_resp->encoder_id,
-                                  DRM_MODE_OBJECT_ENCODER);
-       if (!obj) {
-               ret = -EINVAL;
-               goto out;
-       }
-       encoder = obj_to_encoder(obj);
-
-       if (encoder->crtc)
-               enc_resp->crtc_id = encoder->crtc->base.id;
-       else
-               enc_resp->crtc_id = 0;
-       enc_resp->encoder_type = encoder->encoder_type;
-       enc_resp->encoder_id = encoder->base.id;
-       enc_resp->possible_crtcs = encoder->possible_crtcs;
-       enc_resp->possible_clones = encoder->possible_clones;
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-/**
- * drm_mode_setcrtc - set CRTC configuration
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * LOCKING:
- * Caller? (FIXME)
- *
- * Build a new CRTC configuration based on user request.
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_setcrtc(struct drm_device *dev, void *data,
-                    struct drm_file *file_priv)
-{
-       struct drm_mode_config *config = &dev->mode_config;
-       struct drm_mode_crtc *crtc_req = data;
-       struct drm_mode_object *obj;
-       struct drm_crtc *crtc, *crtcfb;
-       struct drm_connector **connector_set = NULL, *connector;
-       struct drm_framebuffer *fb = NULL;
-       struct drm_display_mode *mode = NULL;
-       struct drm_mode_set set;
-       uint32_t __user *set_connectors_ptr;
-       int ret = 0;
-       int i;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, crtc_req->crtc_id,
-                                  DRM_MODE_OBJECT_CRTC);
-       if (!obj) {
-               DRM_DEBUG_KMS("Unknown CRTC ID %d\n", crtc_req->crtc_id);
-               ret = -EINVAL;
-               goto out;
-       }
-       crtc = obj_to_crtc(obj);
-       DRM_DEBUG_KMS("[CRTC:%d]\n", crtc->base.id);
-
-       if (crtc_req->mode_valid) {
-               /* If we have a mode we need a framebuffer. */
-               /* If we pass -1, set the mode with the currently bound fb */
-               if (crtc_req->fb_id == -1) {
-                       list_for_each_entry(crtcfb,
-                                           &dev->mode_config.crtc_list, head) {
-                               if (crtcfb == crtc) {
-                                       DRM_DEBUG_KMS("Using current fb for "
-                                                       "setmode\n");
-                                       fb = crtc->fb;
-                               }
-                       }
-               } else {
-                       obj = drm_mode_object_find(dev, crtc_req->fb_id,
-                                                  DRM_MODE_OBJECT_FB);
-                       if (!obj) {
-                               DRM_DEBUG_KMS("Unknown FB ID%d\n",
-                                               crtc_req->fb_id);
-                               ret = -EINVAL;
-                               goto out;
-                       }
-                       fb = obj_to_fb(obj);
-               }
-
-               mode = drm_mode_create(dev);
-               drm_crtc_convert_umode(mode, &crtc_req->mode);
-               drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
-       }
-
-       if (crtc_req->count_connectors == 0 && mode) {
-               DRM_DEBUG_KMS("Count connectors is 0 but mode set\n");
-               ret = -EINVAL;
-               goto out;
-       }
-
-       if (crtc_req->count_connectors > 0 && (!mode || !fb)) {
-               DRM_DEBUG_KMS("Count connectors is %d but no mode or fb set\n",
-                         crtc_req->count_connectors);
-               ret = -EINVAL;
-               goto out;
-       }
-
-       if (crtc_req->count_connectors > 0) {
-               u32 out_id;
-
-               /* Avoid unbounded kernel memory allocation */
-               if (crtc_req->count_connectors > config->num_connector) {
-                       ret = -EINVAL;
-                       goto out;
-               }
-
-               connector_set = kmalloc(crtc_req->count_connectors *
-                                       sizeof(struct drm_connector *),
-                                       GFP_KERNEL);
-               if (!connector_set) {
-                       ret = -ENOMEM;
-                       goto out;
-               }
-
-               for (i = 0; i < crtc_req->count_connectors; i++) {
-                       set_connectors_ptr = (uint32_t *)(unsigned long)crtc_req->set_connectors_ptr;
-                       if (get_user(out_id, &set_connectors_ptr[i])) {
-                               ret = -EFAULT;
-                               goto out;
-                       }
-
-                       obj = drm_mode_object_find(dev, out_id,
-                                                  DRM_MODE_OBJECT_CONNECTOR);
-                       if (!obj) {
-                               DRM_DEBUG_KMS("Connector id %d unknown\n",
-                                               out_id);
-                               ret = -EINVAL;
-                               goto out;
-                       }
-                       connector = obj_to_connector(obj);
-                       DRM_DEBUG_KMS("[CONNECTOR:%d:%s]\n",
-                                       connector->base.id,
-                                       drm_get_connector_name(connector));
-
-                       connector_set[i] = connector;
-               }
-       }
-
-       set.crtc = crtc;
-       set.x = crtc_req->x;
-       set.y = crtc_req->y;
-       set.mode = mode;
-       set.connectors = connector_set;
-       set.num_connectors = crtc_req->count_connectors;
-       set.fb = fb;
-       ret = crtc->funcs->set_config(&set);
-
-out:
-       kfree(connector_set);
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-int drm_mode_cursor_ioctl(struct drm_device *dev,
-                       void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_cursor *req = data;
-       struct drm_mode_object *obj;
-       struct drm_crtc *crtc;
-       int ret = 0;
-
-       if (!req->flags) {
-               DRM_ERROR("no operation set\n");
-               return -EINVAL;
-       }
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, req->crtc_id, DRM_MODE_OBJECT_CRTC);
-       if (!obj) {
-               DRM_DEBUG_KMS("Unknown CRTC ID %d\n", req->crtc_id);
-               ret = -EINVAL;
-               goto out;
-       }
-       crtc = obj_to_crtc(obj);
-
-       if (req->flags & DRM_MODE_CURSOR_BO) {
-               if (!crtc->funcs->cursor_set) {
-                       DRM_ERROR("crtc does not support cursor\n");
-                       ret = -ENXIO;
-                       goto out;
-               }
-               /* Turns off the cursor if handle is 0 */
-               ret = crtc->funcs->cursor_set(crtc, file_priv, req->handle,
-                                             req->width, req->height);
-       }
-
-       if (req->flags & DRM_MODE_CURSOR_MOVE) {
-               if (crtc->funcs->cursor_move) {
-                       ret = crtc->funcs->cursor_move(crtc, req->x, req->y);
-               } else {
-                       DRM_ERROR("crtc does not support cursor\n");
-                       ret = -EFAULT;
-                       goto out;
-               }
-       }
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-/**
- * drm_mode_addfb - add an FB to the graphics configuration
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * LOCKING:
- * Takes mode config lock.
- *
- * Add a new FB to the specified CRTC, given a user request.
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_addfb(struct drm_device *dev,
-                  void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_fb_cmd *r = data;
-       struct drm_mode_config *config = &dev->mode_config;
-       struct drm_framebuffer *fb;
-       int ret = 0;
-
-       if ((config->min_width > r->width) || (r->width > config->max_width)) {
-               DRM_ERROR("mode new framebuffer width not within limits\n");
-               return -EINVAL;
-       }
-       if ((config->min_height > r->height) || (r->height > config->max_height)) {
-               DRM_ERROR("mode new framebuffer height not within limits\n");
-               return -EINVAL;
-       }
-
-       mutex_lock(&dev->mode_config.mutex);
-
-       /* TODO check buffer is sufficently large */
-       /* TODO setup destructor callback */
-
-       fb = dev->mode_config.funcs->fb_create(dev, file_priv, r);
-       if (IS_ERR(fb)) {
-               DRM_ERROR("could not create framebuffer\n");
-               ret = PTR_ERR(fb);
-               goto out;
-       }
-
-       r->fb_id = fb->base.id;
-       list_add(&fb->filp_head, &file_priv->fbs);
-       DRM_DEBUG_KMS("[FB:%d]\n", fb->base.id);
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-/**
- * drm_mode_rmfb - remove an FB from the configuration
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * LOCKING:
- * Takes mode config lock.
- *
- * Remove the FB specified by the user.
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_rmfb(struct drm_device *dev,
-                  void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_object *obj;
-       struct drm_framebuffer *fb = NULL;
-       struct drm_framebuffer *fbl = NULL;
-       uint32_t *id = data;
-       int ret = 0;
-       int found = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, *id, DRM_MODE_OBJECT_FB);
-       /* TODO check that we realy get a framebuffer back. */
-       if (!obj) {
-               DRM_ERROR("mode invalid framebuffer id\n");
-               ret = -EINVAL;
-               goto out;
-       }
-       fb = obj_to_fb(obj);
-
-       list_for_each_entry(fbl, &file_priv->fbs, filp_head)
-               if (fb == fbl)
-                       found = 1;
-
-       if (!found) {
-               DRM_ERROR("tried to remove a fb that we didn't own\n");
-               ret = -EINVAL;
-               goto out;
-       }
-
-       /* TODO release all crtc connected to the framebuffer */
-       /* TODO unhock the destructor from the buffer object */
-
-       list_del(&fb->filp_head);
-       fb->funcs->destroy(fb);
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-/**
- * drm_mode_getfb - get FB info
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * LOCKING:
- * Caller? (FIXME)
- *
- * Lookup the FB given its ID and return info about it.
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_getfb(struct drm_device *dev,
-                  void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_fb_cmd *r = data;
-       struct drm_mode_object *obj;
-       struct drm_framebuffer *fb;
-       int ret = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, r->fb_id, DRM_MODE_OBJECT_FB);
-       if (!obj) {
-               DRM_ERROR("invalid framebuffer id\n");
-               ret = -EINVAL;
-               goto out;
-       }
-       fb = obj_to_fb(obj);
-
-       r->height = fb->height;
-       r->width = fb->width;
-       r->depth = fb->depth;
-       r->bpp = fb->bits_per_pixel;
-       r->pitch = fb->pitch;
-       fb->funcs->create_handle(fb, file_priv, &r->handle);
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-int drm_mode_dirtyfb_ioctl(struct drm_device *dev,
-                          void *data, struct drm_file *file_priv)
-{
-       struct drm_clip_rect __user *clips_ptr;
-       struct drm_clip_rect *clips = NULL;
-       struct drm_mode_fb_dirty_cmd *r = data;
-       struct drm_mode_object *obj;
-       struct drm_framebuffer *fb;
-       unsigned flags;
-       int num_clips;
-       int ret = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, r->fb_id, DRM_MODE_OBJECT_FB);
-       if (!obj) {
-               DRM_ERROR("invalid framebuffer id\n");
-               ret = -EINVAL;
-               goto out_err1;
-       }
-       fb = obj_to_fb(obj);
-
-       num_clips = r->num_clips;
-       clips_ptr = (struct drm_clip_rect *)(unsigned long)r->clips_ptr;
-
-       if (!num_clips != !clips_ptr) {
-               ret = -EINVAL;
-               goto out_err1;
-       }
-
-       flags = DRM_MODE_FB_DIRTY_FLAGS & r->flags;
-
-       /* If userspace annotates copy, clips must come in pairs */
-       if (flags & DRM_MODE_FB_DIRTY_ANNOTATE_COPY && (num_clips % 2)) {
-               ret = -EINVAL;
-               goto out_err1;
-       }
-
-       if (num_clips && clips_ptr) {
-               clips = kzalloc(num_clips * sizeof(*clips), GFP_KERNEL);
-               if (!clips) {
-                       ret = -ENOMEM;
-                       goto out_err1;
-               }
-
-               ret = copy_from_user(clips, clips_ptr,
-                                    num_clips * sizeof(*clips));
-               if (ret) {
-                       ret = -EFAULT;
-                       goto out_err2;
-               }
-       }
-
-       if (fb->funcs->dirty) {
-               ret = fb->funcs->dirty(fb, file_priv, flags, r->color,
-                                      clips, num_clips);
-       } else {
-               ret = -ENOSYS;
-               goto out_err2;
-       }
-
-out_err2:
-       kfree(clips);
-out_err1:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-
-/**
- * drm_fb_release - remove and free the FBs on this file
- * @filp: file * from the ioctl
- *
- * LOCKING:
- * Takes mode config lock.
- *
- * Destroy all the FBs associated with @filp.
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-void drm_fb_release(struct drm_file *priv)
-{
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_framebuffer *fb, *tfb;
-
-       mutex_lock(&dev->mode_config.mutex);
-       list_for_each_entry_safe(fb, tfb, &priv->fbs, filp_head) {
-               list_del(&fb->filp_head);
-               fb->funcs->destroy(fb);
-       }
-       mutex_unlock(&dev->mode_config.mutex);
-}
-
-/**
- * drm_mode_attachmode - add a mode to the user mode list
- * @dev: DRM device
- * @connector: connector to add the mode to
- * @mode: mode to add
- *
- * Add @mode to @connector's user mode list.
- */
-static int drm_mode_attachmode(struct drm_device *dev,
-                              struct drm_connector *connector,
-                              struct drm_display_mode *mode)
-{
-       int ret = 0;
-
-       list_add_tail(&mode->head, &connector->user_modes);
-       return ret;
-}
-
-int drm_mode_attachmode_crtc(struct drm_device *dev, struct drm_crtc *crtc,
-                            struct drm_display_mode *mode)
-{
-       struct drm_connector *connector;
-       int ret = 0;
-       struct drm_display_mode *dup_mode;
-       int need_dup = 0;
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               if (!connector->encoder)
-                       break;
-               if (connector->encoder->crtc == crtc) {
-                       if (need_dup)
-                               dup_mode = drm_mode_duplicate(dev, mode);
-                       else
-                               dup_mode = mode;
-                       ret = drm_mode_attachmode(dev, connector, dup_mode);
-                       if (ret)
-                               return ret;
-                       need_dup = 1;
-               }
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_mode_attachmode_crtc);
-
-static int drm_mode_detachmode(struct drm_device *dev,
-                              struct drm_connector *connector,
-                              struct drm_display_mode *mode)
-{
-       int found = 0;
-       int ret = 0;
-       struct drm_display_mode *match_mode, *t;
-
-       list_for_each_entry_safe(match_mode, t, &connector->user_modes, head) {
-               if (drm_mode_equal(match_mode, mode)) {
-                       list_del(&match_mode->head);
-                       drm_mode_destroy(dev, match_mode);
-                       found = 1;
-                       break;
-               }
-       }
-
-       if (!found)
-               ret = -EINVAL;
-
-       return ret;
-}
-
-int drm_mode_detachmode_crtc(struct drm_device *dev, struct drm_display_mode *mode)
-{
-       struct drm_connector *connector;
-
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               drm_mode_detachmode(dev, connector, mode);
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_mode_detachmode_crtc);
-
-/**
- * drm_fb_attachmode - Attach a user mode to an connector
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * This attaches a user specified mode to an connector.
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_attachmode_ioctl(struct drm_device *dev,
-                             void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_mode_cmd *mode_cmd = data;
-       struct drm_connector *connector;
-       struct drm_display_mode *mode;
-       struct drm_mode_object *obj;
-       struct drm_mode_modeinfo *umode = &mode_cmd->mode;
-       int ret = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-
-       obj = drm_mode_object_find(dev, mode_cmd->connector_id, DRM_MODE_OBJECT_CONNECTOR);
-       if (!obj) {
-               ret = -EINVAL;
-               goto out;
-       }
-       connector = obj_to_connector(obj);
-
-       mode = drm_mode_create(dev);
-       if (!mode) {
-               ret = -ENOMEM;
-               goto out;
-       }
-
-       drm_crtc_convert_umode(mode, umode);
-
-       ret = drm_mode_attachmode(dev, connector, mode);
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-
-/**
- * drm_fb_detachmode - Detach a user specified mode from an connector
- * @inode: inode from the ioctl
- * @filp: file * from the ioctl
- * @cmd: cmd from ioctl
- * @arg: arg from ioctl
- *
- * Called by the user via ioctl.
- *
- * RETURNS:
- * Zero on success, errno on failure.
- */
-int drm_mode_detachmode_ioctl(struct drm_device *dev,
-                             void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_object *obj;
-       struct drm_mode_mode_cmd *mode_cmd = data;
-       struct drm_connector *connector;
-       struct drm_display_mode mode;
-       struct drm_mode_modeinfo *umode = &mode_cmd->mode;
-       int ret = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-
-       obj = drm_mode_object_find(dev, mode_cmd->connector_id, DRM_MODE_OBJECT_CONNECTOR);
-       if (!obj) {
-               ret = -EINVAL;
-               goto out;
-       }
-       connector = obj_to_connector(obj);
-
-       drm_crtc_convert_umode(&mode, umode);
-       ret = drm_mode_detachmode(dev, connector, &mode);
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-struct drm_property *drm_property_create(struct drm_device *dev, int flags,
-                                        const char *name, int num_values)
-{
-       struct drm_property *property = NULL;
-
-       property = kzalloc(sizeof(struct drm_property), GFP_KERNEL);
-       if (!property)
-               return NULL;
-
-       if (num_values) {
-               property->values = kzalloc(sizeof(uint64_t)*num_values, GFP_KERNEL);
-               if (!property->values)
-                       goto fail;
-       }
-
-       drm_mode_object_get(dev, &property->base, DRM_MODE_OBJECT_PROPERTY);
-       property->flags = flags;
-       property->num_values = num_values;
-       INIT_LIST_HEAD(&property->enum_blob_list);
-
-       if (name)
-               strncpy(property->name, name, DRM_PROP_NAME_LEN);
-
-       list_add_tail(&property->head, &dev->mode_config.property_list);
-       return property;
-fail:
-       kfree(property);
-       return NULL;
-}
-EXPORT_SYMBOL(drm_property_create);
-
-int drm_property_add_enum(struct drm_property *property, int index,
-                         uint64_t value, const char *name)
-{
-       struct drm_property_enum *prop_enum;
-
-       if (!(property->flags & DRM_MODE_PROP_ENUM))
-               return -EINVAL;
-
-       if (!list_empty(&property->enum_blob_list)) {
-               list_for_each_entry(prop_enum, &property->enum_blob_list, head) {
-                       if (prop_enum->value == value) {
-                               strncpy(prop_enum->name, name, DRM_PROP_NAME_LEN);
-                               prop_enum->name[DRM_PROP_NAME_LEN-1] = '\0';
-                               return 0;
-                       }
-               }
-       }
-
-       prop_enum = kzalloc(sizeof(struct drm_property_enum), GFP_KERNEL);
-       if (!prop_enum)
-               return -ENOMEM;
-
-       strncpy(prop_enum->name, name, DRM_PROP_NAME_LEN);
-       prop_enum->name[DRM_PROP_NAME_LEN-1] = '\0';
-       prop_enum->value = value;
-
-       property->values[index] = value;
-       list_add_tail(&prop_enum->head, &property->enum_blob_list);
-       return 0;
-}
-EXPORT_SYMBOL(drm_property_add_enum);
-
-void drm_property_destroy(struct drm_device *dev, struct drm_property *property)
-{
-       struct drm_property_enum *prop_enum, *pt;
-
-       list_for_each_entry_safe(prop_enum, pt, &property->enum_blob_list, head) {
-               list_del(&prop_enum->head);
-               kfree(prop_enum);
-       }
-
-       if (property->num_values)
-               kfree(property->values);
-       drm_mode_object_put(dev, &property->base);
-       list_del(&property->head);
-       kfree(property);
-}
-EXPORT_SYMBOL(drm_property_destroy);
-
-int drm_connector_attach_property(struct drm_connector *connector,
-                              struct drm_property *property, uint64_t init_val)
-{
-       int i;
-
-       for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
-               if (connector->property_ids[i] == 0) {
-                       connector->property_ids[i] = property->base.id;
-                       connector->property_values[i] = init_val;
-                       break;
-               }
-       }
-
-       if (i == DRM_CONNECTOR_MAX_PROPERTY)
-               return -EINVAL;
-       return 0;
-}
-EXPORT_SYMBOL(drm_connector_attach_property);
-
-int drm_connector_property_set_value(struct drm_connector *connector,
-                                 struct drm_property *property, uint64_t value)
-{
-       int i;
-
-       for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
-               if (connector->property_ids[i] == property->base.id) {
-                       connector->property_values[i] = value;
-                       break;
-               }
-       }
-
-       if (i == DRM_CONNECTOR_MAX_PROPERTY)
-               return -EINVAL;
-       return 0;
-}
-EXPORT_SYMBOL(drm_connector_property_set_value);
-
-int drm_connector_property_get_value(struct drm_connector *connector,
-                                 struct drm_property *property, uint64_t *val)
-{
-       int i;
-
-       for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
-               if (connector->property_ids[i] == property->base.id) {
-                       *val = connector->property_values[i];
-                       break;
-               }
-       }
-
-       if (i == DRM_CONNECTOR_MAX_PROPERTY)
-               return -EINVAL;
-       return 0;
-}
-EXPORT_SYMBOL(drm_connector_property_get_value);
-
-int drm_mode_getproperty_ioctl(struct drm_device *dev,
-                              void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_object *obj;
-       struct drm_mode_get_property *out_resp = data;
-       struct drm_property *property;
-       int enum_count = 0;
-       int blob_count = 0;
-       int value_count = 0;
-       int ret = 0, i;
-       int copied;
-       struct drm_property_enum *prop_enum;
-       struct drm_mode_property_enum __user *enum_ptr;
-       struct drm_property_blob *prop_blob;
-       uint32_t *blob_id_ptr;
-       uint64_t __user *values_ptr;
-       uint32_t __user *blob_length_ptr;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, out_resp->prop_id, DRM_MODE_OBJECT_PROPERTY);
-       if (!obj) {
-               ret = -EINVAL;
-               goto done;
-       }
-       property = obj_to_property(obj);
-
-       if (property->flags & DRM_MODE_PROP_ENUM) {
-               list_for_each_entry(prop_enum, &property->enum_blob_list, head)
-                       enum_count++;
-       } else if (property->flags & DRM_MODE_PROP_BLOB) {
-               list_for_each_entry(prop_blob, &property->enum_blob_list, head)
-                       blob_count++;
-       }
-
-       value_count = property->num_values;
-
-       strncpy(out_resp->name, property->name, DRM_PROP_NAME_LEN);
-       out_resp->name[DRM_PROP_NAME_LEN-1] = 0;
-       out_resp->flags = property->flags;
-
-       if ((out_resp->count_values >= value_count) && value_count) {
-               values_ptr = (uint64_t *)(unsigned long)out_resp->values_ptr;
-               for (i = 0; i < value_count; i++) {
-                       if (copy_to_user(values_ptr + i, &property->values[i], sizeof(uint64_t))) {
-                               ret = -EFAULT;
-                               goto done;
-                       }
-               }
-       }
-       out_resp->count_values = value_count;
-
-       if (property->flags & DRM_MODE_PROP_ENUM) {
-               if ((out_resp->count_enum_blobs >= enum_count) && enum_count) {
-                       copied = 0;
-                       enum_ptr = (struct drm_mode_property_enum *)(unsigned long)out_resp->enum_blob_ptr;
-                       list_for_each_entry(prop_enum, &property->enum_blob_list, head) {
-
-                               if (copy_to_user(&enum_ptr[copied].value, &prop_enum->value, sizeof(uint64_t))) {
-                                       ret = -EFAULT;
-                                       goto done;
-                               }
-
-                               if (copy_to_user(&enum_ptr[copied].name,
-                                                &prop_enum->name, DRM_PROP_NAME_LEN)) {
-                                       ret = -EFAULT;
-                                       goto done;
-                               }
-                               copied++;
-                       }
-               }
-               out_resp->count_enum_blobs = enum_count;
-       }
-
-       if (property->flags & DRM_MODE_PROP_BLOB) {
-               if ((out_resp->count_enum_blobs >= blob_count) && blob_count) {
-                       copied = 0;
-                       blob_id_ptr = (uint32_t *)(unsigned long)out_resp->enum_blob_ptr;
-                       blob_length_ptr = (uint32_t *)(unsigned long)out_resp->values_ptr;
-
-                       list_for_each_entry(prop_blob, &property->enum_blob_list, head) {
-                               if (put_user(prop_blob->base.id, blob_id_ptr + copied)) {
-                                       ret = -EFAULT;
-                                       goto done;
-                               }
-
-                               if (put_user(prop_blob->length, blob_length_ptr + copied)) {
-                                       ret = -EFAULT;
-                                       goto done;
-                               }
-
-                               copied++;
-                       }
-               }
-               out_resp->count_enum_blobs = blob_count;
-       }
-done:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-static struct drm_property_blob *drm_property_create_blob(struct drm_device *dev, int length,
-                                                         void *data)
-{
-       struct drm_property_blob *blob;
-
-       if (!length || !data)
-               return NULL;
-
-       blob = kzalloc(sizeof(struct drm_property_blob)+length, GFP_KERNEL);
-       if (!blob)
-               return NULL;
-
-       blob->data = (void *)((char *)blob + sizeof(struct drm_property_blob));
-       blob->length = length;
-
-       memcpy(blob->data, data, length);
-
-       drm_mode_object_get(dev, &blob->base, DRM_MODE_OBJECT_BLOB);
-
-       list_add_tail(&blob->head, &dev->mode_config.property_blob_list);
-       return blob;
-}
-
-static void drm_property_destroy_blob(struct drm_device *dev,
-                              struct drm_property_blob *blob)
-{
-       drm_mode_object_put(dev, &blob->base);
-       list_del(&blob->head);
-       kfree(blob);
-}
-
-int drm_mode_getblob_ioctl(struct drm_device *dev,
-                          void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_object *obj;
-       struct drm_mode_get_blob *out_resp = data;
-       struct drm_property_blob *blob;
-       int ret = 0;
-       void *blob_ptr;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, out_resp->blob_id, DRM_MODE_OBJECT_BLOB);
-       if (!obj) {
-               ret = -EINVAL;
-               goto done;
-       }
-       blob = obj_to_blob(obj);
-
-       if (out_resp->length == blob->length) {
-               blob_ptr = (void *)(unsigned long)out_resp->data;
-               if (copy_to_user(blob_ptr, blob->data, blob->length)){
-                       ret = -EFAULT;
-                       goto done;
-               }
-       }
-       out_resp->length = blob->length;
-
-done:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-int drm_mode_connector_update_edid_property(struct drm_connector *connector,
-                                           struct edid *edid)
-{
-       struct drm_device *dev = connector->dev;
-       int ret = 0, size;
-
-       if (connector->edid_blob_ptr)
-               drm_property_destroy_blob(dev, connector->edid_blob_ptr);
-
-       /* Delete edid, when there is none. */
-       if (!edid) {
-               connector->edid_blob_ptr = NULL;
-               ret = drm_connector_property_set_value(connector, dev->mode_config.edid_property, 0);
-               return ret;
-       }
-
-       size = EDID_LENGTH * (1 + edid->extensions);
-       connector->edid_blob_ptr = drm_property_create_blob(connector->dev,
-                                                           size, edid);
-
-       ret = drm_connector_property_set_value(connector,
-                                              dev->mode_config.edid_property,
-                                              connector->edid_blob_ptr->base.id);
-
-       return ret;
-}
-EXPORT_SYMBOL(drm_mode_connector_update_edid_property);
-
-int drm_mode_connector_property_set_ioctl(struct drm_device *dev,
-                                      void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_connector_set_property *out_resp = data;
-       struct drm_mode_object *obj;
-       struct drm_property *property;
-       struct drm_connector *connector;
-       int ret = -EINVAL;
-       int i;
-
-       mutex_lock(&dev->mode_config.mutex);
-
-       obj = drm_mode_object_find(dev, out_resp->connector_id, DRM_MODE_OBJECT_CONNECTOR);
-       if (!obj) {
-               goto out;
-       }
-       connector = obj_to_connector(obj);
-
-       for (i = 0; i < DRM_CONNECTOR_MAX_PROPERTY; i++) {
-               if (connector->property_ids[i] == out_resp->prop_id)
-                       break;
-       }
-
-       if (i == DRM_CONNECTOR_MAX_PROPERTY) {
-               goto out;
-       }
-
-       obj = drm_mode_object_find(dev, out_resp->prop_id, DRM_MODE_OBJECT_PROPERTY);
-       if (!obj) {
-               goto out;
-       }
-       property = obj_to_property(obj);
-
-       if (property->flags & DRM_MODE_PROP_IMMUTABLE)
-               goto out;
-
-       if (property->flags & DRM_MODE_PROP_RANGE) {
-               if (out_resp->value < property->values[0])
-                       goto out;
-
-               if (out_resp->value > property->values[1])
-                       goto out;
-       } else {
-               int found = 0;
-               for (i = 0; i < property->num_values; i++) {
-                       if (property->values[i] == out_resp->value) {
-                               found = 1;
-                               break;
-                       }
-               }
-               if (!found) {
-                       goto out;
-               }
-       }
-
-       /* Do DPMS ourselves */
-       if (property == connector->dev->mode_config.dpms_property) {
-               if (connector->funcs->dpms)
-                       (*connector->funcs->dpms)(connector, (int) out_resp->value);
-               ret = 0;
-       } else if (connector->funcs->set_property)
-               ret = connector->funcs->set_property(connector, property, out_resp->value);
-
-       /* store the property value if successful */
-       if (!ret)
-               drm_connector_property_set_value(connector, property, out_resp->value);
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-int drm_mode_connector_attach_encoder(struct drm_connector *connector,
-                                     struct drm_encoder *encoder)
-{
-       int i;
-
-       for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
-               if (connector->encoder_ids[i] == 0) {
-                       connector->encoder_ids[i] = encoder->base.id;
-                       return 0;
-               }
-       }
-       return -ENOMEM;
-}
-EXPORT_SYMBOL(drm_mode_connector_attach_encoder);
-
-void drm_mode_connector_detach_encoder(struct drm_connector *connector,
-                                   struct drm_encoder *encoder)
-{
-       int i;
-       for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
-               if (connector->encoder_ids[i] == encoder->base.id) {
-                       connector->encoder_ids[i] = 0;
-                       if (connector->encoder == encoder)
-                               connector->encoder = NULL;
-                       break;
-               }
-       }
-}
-EXPORT_SYMBOL(drm_mode_connector_detach_encoder);
-
-bool drm_mode_crtc_set_gamma_size(struct drm_crtc *crtc,
-                                 int gamma_size)
-{
-       crtc->gamma_size = gamma_size;
-
-       crtc->gamma_store = kzalloc(gamma_size * sizeof(uint16_t) * 3, GFP_KERNEL);
-       if (!crtc->gamma_store) {
-               crtc->gamma_size = 0;
-               return false;
-       }
-
-       return true;
-}
-EXPORT_SYMBOL(drm_mode_crtc_set_gamma_size);
-
-int drm_mode_gamma_set_ioctl(struct drm_device *dev,
-                            void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_crtc_lut *crtc_lut = data;
-       struct drm_mode_object *obj;
-       struct drm_crtc *crtc;
-       void *r_base, *g_base, *b_base;
-       int size;
-       int ret = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, crtc_lut->crtc_id, DRM_MODE_OBJECT_CRTC);
-       if (!obj) {
-               ret = -EINVAL;
-               goto out;
-       }
-       crtc = obj_to_crtc(obj);
-
-       /* memcpy into gamma store */
-       if (crtc_lut->gamma_size != crtc->gamma_size) {
-               ret = -EINVAL;
-               goto out;
-       }
-
-       size = crtc_lut->gamma_size * (sizeof(uint16_t));
-       r_base = crtc->gamma_store;
-       if (copy_from_user(r_base, (void __user *)(unsigned long)crtc_lut->red, size)) {
-               ret = -EFAULT;
-               goto out;
-       }
-
-       g_base = r_base + size;
-       if (copy_from_user(g_base, (void __user *)(unsigned long)crtc_lut->green, size)) {
-               ret = -EFAULT;
-               goto out;
-       }
-
-       b_base = g_base + size;
-       if (copy_from_user(b_base, (void __user *)(unsigned long)crtc_lut->blue, size)) {
-               ret = -EFAULT;
-               goto out;
-       }
-
-       crtc->funcs->gamma_set(crtc, r_base, g_base, b_base, 0, crtc->gamma_size);
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-
-}
-
-int drm_mode_gamma_get_ioctl(struct drm_device *dev,
-                            void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_crtc_lut *crtc_lut = data;
-       struct drm_mode_object *obj;
-       struct drm_crtc *crtc;
-       void *r_base, *g_base, *b_base;
-       int size;
-       int ret = 0;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, crtc_lut->crtc_id, DRM_MODE_OBJECT_CRTC);
-       if (!obj) {
-               ret = -EINVAL;
-               goto out;
-       }
-       crtc = obj_to_crtc(obj);
-
-       /* memcpy into gamma store */
-       if (crtc_lut->gamma_size != crtc->gamma_size) {
-               ret = -EINVAL;
-               goto out;
-       }
-
-       size = crtc_lut->gamma_size * (sizeof(uint16_t));
-       r_base = crtc->gamma_store;
-       if (copy_to_user((void __user *)(unsigned long)crtc_lut->red, r_base, size)) {
-               ret = -EFAULT;
-               goto out;
-       }
-
-       g_base = r_base + size;
-       if (copy_to_user((void __user *)(unsigned long)crtc_lut->green, g_base, size)) {
-               ret = -EFAULT;
-               goto out;
-       }
-
-       b_base = g_base + size;
-       if (copy_to_user((void __user *)(unsigned long)crtc_lut->blue, b_base, size)) {
-               ret = -EFAULT;
-               goto out;
-       }
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-
-int drm_mode_page_flip_ioctl(struct drm_device *dev,
-                            void *data, struct drm_file *file_priv)
-{
-       struct drm_mode_crtc_page_flip *page_flip = data;
-       struct drm_mode_object *obj;
-       struct drm_crtc *crtc;
-       struct drm_framebuffer *fb;
-       struct drm_pending_vblank_event *e = NULL;
-       unsigned long flags;
-       int ret = -EINVAL;
-
-       if (page_flip->flags & ~DRM_MODE_PAGE_FLIP_FLAGS ||
-           page_flip->reserved != 0)
-               return -EINVAL;
-
-       mutex_lock(&dev->mode_config.mutex);
-       obj = drm_mode_object_find(dev, page_flip->crtc_id, DRM_MODE_OBJECT_CRTC);
-       if (!obj)
-               goto out;
-       crtc = obj_to_crtc(obj);
-
-       if (crtc->fb == NULL) {
-               /* The framebuffer is currently unbound, presumably
-                * due to a hotplug event, that userspace has not
-                * yet discovered.
-                */
-               ret = -EBUSY;
-               goto out;
-       }
-
-       if (crtc->funcs->page_flip == NULL)
-               goto out;
-
-       obj = drm_mode_object_find(dev, page_flip->fb_id, DRM_MODE_OBJECT_FB);
-       if (!obj)
-               goto out;
-       fb = obj_to_fb(obj);
-
-       if (page_flip->flags & DRM_MODE_PAGE_FLIP_EVENT) {
-               ret = -ENOMEM;
-               spin_lock_irqsave(&dev->event_lock, flags);
-               if (file_priv->event_space < sizeof e->event) {
-                       spin_unlock_irqrestore(&dev->event_lock, flags);
-                       goto out;
-               }
-               file_priv->event_space -= sizeof e->event;
-               spin_unlock_irqrestore(&dev->event_lock, flags);
-
-               e = kzalloc(sizeof *e, GFP_KERNEL);
-               if (e == NULL) {
-                       spin_lock_irqsave(&dev->event_lock, flags);
-                       file_priv->event_space += sizeof e->event;
-                       spin_unlock_irqrestore(&dev->event_lock, flags);
-                       goto out;
-               }
-
-               e->event.base.type = DRM_EVENT_FLIP_COMPLETE;
-               e->event.base.length = sizeof e->event;
-               e->event.user_data = page_flip->user_data;
-               e->base.event = &e->event.base;
-               e->base.file_priv = file_priv;
-               e->base.destroy =
-                       (void (*) (struct drm_pending_event *)) kfree;
-       }
-
-       ret = crtc->funcs->page_flip(crtc, fb, e);
-       if (ret) {
-               spin_lock_irqsave(&dev->event_lock, flags);
-               file_priv->event_space += sizeof e->event;
-               spin_unlock_irqrestore(&dev->event_lock, flags);
-               kfree(e);
-       }
-
-out:
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
diff --git a/services4/3rdparty/linux_drm/drm_crtc_helper.c b/services4/3rdparty/linux_drm/drm_crtc_helper.c
deleted file mode 100644 (file)
index 2d4e17a..0000000
+++ /dev/null
@@ -1,949 +0,0 @@
-/*
- * Copyright (c) 2006-2008 Intel Corporation
- * Copyright (c) 2007 Dave Airlie <airlied@linux.ie>
- *
- * DRM core CRTC related functions
- *
- * Permission to use, copy, modify, distribute, and sell this software and its
- * documentation for any purpose is hereby granted without fee, provided that
- * the above copyright notice appear in all copies and that both that copyright
- * notice and this permission notice appear in supporting documentation, and
- * that the name of the copyright holders not be used in advertising or
- * publicity pertaining to distribution of the software without specific,
- * written prior permission.  The copyright holders make no representations
- * about the suitability of this software for any purpose.  It is provided "as
- * is" without express or implied warranty.
- *
- * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
- * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
- * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
- * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
- * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
- * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
- * OF THIS SOFTWARE.
- *
- * Authors:
- *      Keith Packard
- *     Eric Anholt <eric@anholt.net>
- *      Dave Airlie <airlied@linux.ie>
- *      Jesse Barnes <jesse.barnes@intel.com>
- */
-
-#include "drmP.h"
-#include "drm_crtc.h"
-#include "drm_crtc_helper.h"
-#include "drm_fb_helper.h"
-
-static bool drm_kms_helper_poll = true;
-module_param_named(poll, drm_kms_helper_poll, bool, 0600);
-
-static void drm_mode_validate_flag(struct drm_connector *connector,
-                                  int flags)
-{
-       struct drm_display_mode *mode, *t;
-
-       if (flags == (DRM_MODE_FLAG_DBLSCAN | DRM_MODE_FLAG_INTERLACE))
-               return;
-
-       list_for_each_entry_safe(mode, t, &connector->modes, head) {
-               if ((mode->flags & DRM_MODE_FLAG_INTERLACE) &&
-                               !(flags & DRM_MODE_FLAG_INTERLACE))
-                       mode->status = MODE_NO_INTERLACE;
-               if ((mode->flags & DRM_MODE_FLAG_DBLSCAN) &&
-                               !(flags & DRM_MODE_FLAG_DBLSCAN))
-                       mode->status = MODE_NO_DBLESCAN;
-       }
-
-       return;
-}
-
-/**
- * drm_helper_probe_single_connector_modes - get complete set of display modes
- * @dev: DRM device
- * @maxX: max width for modes
- * @maxY: max height for modes
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Based on @dev's mode_config layout, scan all the connectors and try to detect
- * modes on them.  Modes will first be added to the connector's probed_modes
- * list, then culled (based on validity and the @maxX, @maxY parameters) and
- * put into the normal modes list.
- *
- * Intended to be used either at bootup time or when major configuration
- * changes have occurred.
- *
- * FIXME: take into account monitor limits
- *
- * RETURNS:
- * Number of modes found on @connector.
- */
-int drm_helper_probe_single_connector_modes(struct drm_connector *connector,
-                                           uint32_t maxX, uint32_t maxY)
-{
-       struct drm_device *dev = connector->dev;
-       struct drm_display_mode *mode, *t;
-       struct drm_connector_helper_funcs *connector_funcs =
-               connector->helper_private;
-       int count = 0;
-       int mode_flags = 0;
-
-       DRM_DEBUG_KMS("[CONNECTOR:%d:%s]\n", connector->base.id,
-                       drm_get_connector_name(connector));
-       /* set all modes to the unverified state */
-       list_for_each_entry_safe(mode, t, &connector->modes, head)
-               mode->status = MODE_UNVERIFIED;
-
-       if (connector->force) {
-               if (connector->force == DRM_FORCE_ON)
-                       connector->status = connector_status_connected;
-               else
-                       connector->status = connector_status_disconnected;
-               if (connector->funcs->force)
-                       connector->funcs->force(connector);
-       } else {
-               connector->status = connector->funcs->detect(connector, true);
-               drm_kms_helper_poll_enable(dev);
-       }
-
-       if (connector->status == connector_status_disconnected) {
-               DRM_DEBUG_KMS("[CONNECTOR:%d:%s] disconnected\n",
-                       connector->base.id, drm_get_connector_name(connector));
-               drm_mode_connector_update_edid_property(connector, NULL);
-               goto prune;
-       }
-
-       count = (*connector_funcs->get_modes)(connector);
-       if (count == 0 && connector->status == connector_status_connected)
-               count = drm_add_modes_noedid(connector, 1024, 768);
-       if (count == 0)
-               goto prune;
-
-       drm_mode_connector_list_update(connector);
-
-       if (maxX && maxY)
-               drm_mode_validate_size(dev, &connector->modes, maxX,
-                                      maxY, 0);
-
-       if (connector->interlace_allowed)
-               mode_flags |= DRM_MODE_FLAG_INTERLACE;
-       if (connector->doublescan_allowed)
-               mode_flags |= DRM_MODE_FLAG_DBLSCAN;
-       drm_mode_validate_flag(connector, mode_flags);
-
-       list_for_each_entry_safe(mode, t, &connector->modes, head) {
-               if (mode->status == MODE_OK)
-                       mode->status = connector_funcs->mode_valid(connector,
-                                                                  mode);
-       }
-
-prune:
-       drm_mode_prune_invalid(dev, &connector->modes, true);
-
-       if (list_empty(&connector->modes))
-               return 0;
-
-       drm_mode_sort(&connector->modes);
-
-       DRM_DEBUG_KMS("[CONNECTOR:%d:%s] probed modes :\n", connector->base.id,
-                       drm_get_connector_name(connector));
-       list_for_each_entry_safe(mode, t, &connector->modes, head) {
-               mode->vrefresh = drm_mode_vrefresh(mode);
-
-               drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
-               drm_mode_debug_printmodeline(mode);
-       }
-
-       return count;
-}
-EXPORT_SYMBOL(drm_helper_probe_single_connector_modes);
-
-/**
- * drm_helper_encoder_in_use - check if a given encoder is in use
- * @encoder: encoder to check
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Walk @encoders's DRM device's mode_config and see if it's in use.
- *
- * RETURNS:
- * True if @encoder is part of the mode_config, false otherwise.
- */
-bool drm_helper_encoder_in_use(struct drm_encoder *encoder)
-{
-       struct drm_connector *connector;
-       struct drm_device *dev = encoder->dev;
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head)
-               if (connector->encoder == encoder)
-                       return true;
-       return false;
-}
-EXPORT_SYMBOL(drm_helper_encoder_in_use);
-
-/**
- * drm_helper_crtc_in_use - check if a given CRTC is in a mode_config
- * @crtc: CRTC to check
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Walk @crtc's DRM device's mode_config and see if it's in use.
- *
- * RETURNS:
- * True if @crtc is part of the mode_config, false otherwise.
- */
-bool drm_helper_crtc_in_use(struct drm_crtc *crtc)
-{
-       struct drm_encoder *encoder;
-       struct drm_device *dev = crtc->dev;
-       /* FIXME: Locking around list access? */
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head)
-               if (encoder->crtc == crtc && drm_helper_encoder_in_use(encoder))
-                       return true;
-       return false;
-}
-EXPORT_SYMBOL(drm_helper_crtc_in_use);
-
-static void
-drm_encoder_disable(struct drm_encoder *encoder)
-{
-       struct drm_encoder_helper_funcs *encoder_funcs = encoder->helper_private;
-
-       if (encoder_funcs->disable)
-               (*encoder_funcs->disable)(encoder);
-       else
-               (*encoder_funcs->dpms)(encoder, DRM_MODE_DPMS_OFF);
-}
-
-/**
- * drm_helper_disable_unused_functions - disable unused objects
- * @dev: DRM device
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * If an connector or CRTC isn't part of @dev's mode_config, it can be disabled
- * by calling its dpms function, which should power it off.
- */
-void drm_helper_disable_unused_functions(struct drm_device *dev)
-{
-       struct drm_encoder *encoder;
-       struct drm_connector *connector;
-       struct drm_crtc *crtc;
-
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               if (!connector->encoder)
-                       continue;
-               if (connector->status == connector_status_disconnected)
-                       connector->encoder = NULL;
-       }
-
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-               if (!drm_helper_encoder_in_use(encoder)) {
-                       drm_encoder_disable(encoder);
-                       /* disconnector encoder from any connector */
-                       encoder->crtc = NULL;
-               }
-       }
-
-       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
-               struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
-               crtc->enabled = drm_helper_crtc_in_use(crtc);
-               if (!crtc->enabled) {
-                       if (crtc_funcs->disable)
-                               (*crtc_funcs->disable)(crtc);
-                       else
-                               (*crtc_funcs->dpms)(crtc, DRM_MODE_DPMS_OFF);
-                       crtc->fb = NULL;
-               }
-       }
-}
-EXPORT_SYMBOL(drm_helper_disable_unused_functions);
-
-/**
- * drm_encoder_crtc_ok - can a given crtc drive a given encoder?
- * @encoder: encoder to test
- * @crtc: crtc to test
- *
- * Return false if @encoder can't be driven by @crtc, true otherwise.
- */
-static bool drm_encoder_crtc_ok(struct drm_encoder *encoder,
-                               struct drm_crtc *crtc)
-{
-       struct drm_device *dev;
-       struct drm_crtc *tmp;
-       int crtc_mask = 1;
-
-       WARN(!crtc, "checking null crtc?\n");
-
-       dev = crtc->dev;
-
-       list_for_each_entry(tmp, &dev->mode_config.crtc_list, head) {
-               if (tmp == crtc)
-                       break;
-               crtc_mask <<= 1;
-       }
-
-       if (encoder->possible_crtcs & crtc_mask)
-               return true;
-       return false;
-}
-
-/*
- * Check the CRTC we're going to map each output to vs. its current
- * CRTC.  If they don't match, we have to disable the output and the CRTC
- * since the driver will have to re-route things.
- */
-static void
-drm_crtc_prepare_encoders(struct drm_device *dev)
-{
-       struct drm_encoder_helper_funcs *encoder_funcs;
-       struct drm_encoder *encoder;
-
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-               encoder_funcs = encoder->helper_private;
-               /* Disable unused encoders */
-               if (encoder->crtc == NULL)
-                       drm_encoder_disable(encoder);
-               /* Disable encoders whose CRTC is about to change */
-               if (encoder_funcs->get_crtc &&
-                   encoder->crtc != (*encoder_funcs->get_crtc)(encoder))
-                       drm_encoder_disable(encoder);
-       }
-}
-
-/**
- * drm_crtc_set_mode - set a mode
- * @crtc: CRTC to program
- * @mode: mode to use
- * @x: width of mode
- * @y: height of mode
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Try to set @mode on @crtc.  Give @crtc and its associated connectors a chance
- * to fixup or reject the mode prior to trying to set it.
- *
- * RETURNS:
- * True if the mode was set successfully, or false otherwise.
- */
-bool drm_crtc_helper_set_mode(struct drm_crtc *crtc,
-                             struct drm_display_mode *mode,
-                             int x, int y,
-                             struct drm_framebuffer *old_fb)
-{
-       struct drm_device *dev = crtc->dev;
-       struct drm_display_mode *adjusted_mode, saved_mode;
-       struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
-       struct drm_encoder_helper_funcs *encoder_funcs;
-       int saved_x, saved_y;
-       struct drm_encoder *encoder;
-       bool ret = true;
-
-       adjusted_mode = drm_mode_duplicate(dev, mode);
-
-       crtc->enabled = drm_helper_crtc_in_use(crtc);
-
-       if (!crtc->enabled)
-               return true;
-
-       saved_mode = crtc->mode;
-       saved_x = crtc->x;
-       saved_y = crtc->y;
-
-       /* Update crtc values up front so the driver can rely on them for mode
-        * setting.
-        */
-       crtc->mode = *mode;
-       crtc->x = x;
-       crtc->y = y;
-
-       /* Pass our mode to the connectors and the CRTC to give them a chance to
-        * adjust it according to limitations or connector properties, and also
-        * a chance to reject the mode entirely.
-        */
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-
-               if (encoder->crtc != crtc)
-                       continue;
-               encoder_funcs = encoder->helper_private;
-               if (!(ret = encoder_funcs->mode_fixup(encoder, mode,
-                                                     adjusted_mode))) {
-                       goto done;
-               }
-       }
-
-       if (!(ret = crtc_funcs->mode_fixup(crtc, mode, adjusted_mode))) {
-               goto done;
-       }
-       DRM_DEBUG_KMS("[CRTC:%d]\n", crtc->base.id);
-
-       /* Prepare the encoders and CRTCs before setting the mode. */
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-
-               if (encoder->crtc != crtc)
-                       continue;
-               encoder_funcs = encoder->helper_private;
-               /* Disable the encoders as the first thing we do. */
-               encoder_funcs->prepare(encoder);
-       }
-
-       drm_crtc_prepare_encoders(dev);
-
-       crtc_funcs->prepare(crtc);
-
-       /* Set up the DPLL and any encoders state that needs to adjust or depend
-        * on the DPLL.
-        */
-       ret = !crtc_funcs->mode_set(crtc, mode, adjusted_mode, x, y, old_fb);
-       if (!ret)
-           goto done;
-
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-
-               if (encoder->crtc != crtc)
-                       continue;
-
-               DRM_DEBUG_KMS("[ENCODER:%d:%s] set [MODE:%d:%s]\n",
-                       encoder->base.id, drm_get_encoder_name(encoder),
-                       mode->base.id, mode->name);
-               encoder_funcs = encoder->helper_private;
-               encoder_funcs->mode_set(encoder, mode, adjusted_mode);
-       }
-
-       /* Now enable the clocks, plane, pipe, and connectors that we set up. */
-       crtc_funcs->commit(crtc);
-
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-
-               if (encoder->crtc != crtc)
-                       continue;
-
-               encoder_funcs = encoder->helper_private;
-               encoder_funcs->commit(encoder);
-
-       }
-
-       /* XXX free adjustedmode */
-       drm_mode_destroy(dev, adjusted_mode);
-       /* FIXME: add subpixel order */
-done:
-       if (!ret) {
-               crtc->mode = saved_mode;
-               crtc->x = saved_x;
-               crtc->y = saved_y;
-       }
-
-       return ret;
-}
-EXPORT_SYMBOL(drm_crtc_helper_set_mode);
-
-
-/**
- * drm_crtc_helper_set_config - set a new config from userspace
- * @crtc: CRTC to setup
- * @crtc_info: user provided configuration
- * @new_mode: new mode to set
- * @connector_set: set of connectors for the new config
- * @fb: new framebuffer
- *
- * LOCKING:
- * Caller must hold mode config lock.
- *
- * Setup a new configuration, provided by the user in @crtc_info, and enable
- * it.
- *
- * RETURNS:
- * Zero. (FIXME)
- */
-int drm_crtc_helper_set_config(struct drm_mode_set *set)
-{
-       struct drm_device *dev;
-       struct drm_crtc *save_crtcs, *new_crtc, *crtc;
-       struct drm_encoder *save_encoders, *new_encoder, *encoder;
-       struct drm_framebuffer *old_fb = NULL;
-       bool mode_changed = false; /* if true do a full mode set */
-       bool fb_changed = false; /* if true and !mode_changed just do a flip */
-       struct drm_connector *save_connectors, *connector;
-       int count = 0, ro, fail = 0;
-       struct drm_crtc_helper_funcs *crtc_funcs;
-       int ret = 0;
-       int i;
-
-       DRM_DEBUG_KMS("\n");
-
-       if (!set)
-               return -EINVAL;
-
-       if (!set->crtc)
-               return -EINVAL;
-
-       if (!set->crtc->helper_private)
-               return -EINVAL;
-
-       crtc_funcs = set->crtc->helper_private;
-
-       if (set->fb) {
-               DRM_DEBUG_KMS("[CRTC:%d] [FB:%d] #connectors=%d (x y) (%i %i)\n",
-                               set->crtc->base.id, set->fb->base.id,
-                               (int)set->num_connectors, set->x, set->y);
-       } else {
-               DRM_DEBUG_KMS("[CRTC:%d] [NOFB] #connectors=%d (x y) (%i %i)\n",
-                               set->crtc->base.id, (int)set->num_connectors,
-                               set->x, set->y);
-       }
-
-       dev = set->crtc->dev;
-
-       /* Allocate space for the backup of all (non-pointer) crtc, encoder and
-        * connector data. */
-       save_crtcs = kzalloc(dev->mode_config.num_crtc *
-                            sizeof(struct drm_crtc), GFP_KERNEL);
-       if (!save_crtcs)
-               return -ENOMEM;
-
-       save_encoders = kzalloc(dev->mode_config.num_encoder *
-                               sizeof(struct drm_encoder), GFP_KERNEL);
-       if (!save_encoders) {
-               kfree(save_crtcs);
-               return -ENOMEM;
-       }
-
-       save_connectors = kzalloc(dev->mode_config.num_connector *
-                               sizeof(struct drm_connector), GFP_KERNEL);
-       if (!save_connectors) {
-               kfree(save_crtcs);
-               kfree(save_encoders);
-               return -ENOMEM;
-       }
-
-       /* Copy data. Note that driver private data is not affected.
-        * Should anything bad happen only the expected state is
-        * restored, not the drivers personal bookkeeping.
-        */
-       count = 0;
-       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
-               save_crtcs[count++] = *crtc;
-       }
-
-       count = 0;
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-               save_encoders[count++] = *encoder;
-       }
-
-       count = 0;
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               save_connectors[count++] = *connector;
-       }
-
-       /* We should be able to check here if the fb has the same properties
-        * and then just flip_or_move it */
-       if (set->crtc->fb != set->fb) {
-               /* If we have no fb then treat it as a full mode set */
-               if (set->crtc->fb == NULL) {
-                       DRM_DEBUG_KMS("crtc has no fb, full mode set\n");
-                       mode_changed = true;
-               } else if (set->fb == NULL) {
-                       mode_changed = true;
-               } else
-                       fb_changed = true;
-       }
-
-       if (set->x != set->crtc->x || set->y != set->crtc->y)
-               fb_changed = true;
-
-       if (set->mode && !drm_mode_equal(set->mode, &set->crtc->mode)) {
-               DRM_DEBUG_KMS("modes are different, full mode set\n");
-               drm_mode_debug_printmodeline(&set->crtc->mode);
-               drm_mode_debug_printmodeline(set->mode);
-               mode_changed = true;
-       }
-
-       /* a) traverse passed in connector list and get encoders for them */
-       count = 0;
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               struct drm_connector_helper_funcs *connector_funcs =
-                       connector->helper_private;
-               new_encoder = connector->encoder;
-               for (ro = 0; ro < set->num_connectors; ro++) {
-                       if (set->connectors[ro] == connector) {
-                               new_encoder = connector_funcs->best_encoder(connector);
-                               /* if we can't get an encoder for a connector
-                                  we are setting now - then fail */
-                               if (new_encoder == NULL)
-                                       /* don't break so fail path works correct */
-                                       fail = 1;
-                               break;
-                       }
-               }
-
-               if (new_encoder != connector->encoder) {
-                       DRM_DEBUG_KMS("encoder changed, full mode switch\n");
-                       mode_changed = true;
-                       /* If the encoder is reused for another connector, then
-                        * the appropriate crtc will be set later.
-                        */
-                       if (connector->encoder)
-                               connector->encoder->crtc = NULL;
-                       connector->encoder = new_encoder;
-               }
-       }
-
-       if (fail) {
-               ret = -EINVAL;
-               goto fail;
-       }
-
-       count = 0;
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               if (!connector->encoder)
-                       continue;
-
-               if (connector->encoder->crtc == set->crtc)
-                       new_crtc = NULL;
-               else
-                       new_crtc = connector->encoder->crtc;
-
-               for (ro = 0; ro < set->num_connectors; ro++) {
-                       if (set->connectors[ro] == connector)
-                               new_crtc = set->crtc;
-               }
-
-               /* Make sure the new CRTC will work with the encoder */
-               if (new_crtc &&
-                   !drm_encoder_crtc_ok(connector->encoder, new_crtc)) {
-                       ret = -EINVAL;
-                       goto fail;
-               }
-               if (new_crtc != connector->encoder->crtc) {
-                       DRM_DEBUG_KMS("crtc changed, full mode switch\n");
-                       mode_changed = true;
-                       connector->encoder->crtc = new_crtc;
-               }
-               if (new_crtc) {
-                       DRM_DEBUG_KMS("[CONNECTOR:%d:%s] to [CRTC:%d]\n",
-                               connector->base.id, drm_get_connector_name(connector),
-                               new_crtc->base.id);
-               } else {
-                       DRM_DEBUG_KMS("[CONNECTOR:%d:%s] to [NOCRTC]\n",
-                               connector->base.id, drm_get_connector_name(connector));
-               }
-       }
-
-       /* mode_set_base is not a required function */
-       if (fb_changed && !crtc_funcs->mode_set_base)
-               mode_changed = true;
-
-       if (mode_changed) {
-               set->crtc->enabled = (set->mode != NULL);
-               if (set->mode != NULL) {
-                       DRM_DEBUG_KMS("attempting to set mode from"
-                                       " userspace\n");
-                       drm_mode_debug_printmodeline(set->mode);
-                       old_fb = set->crtc->fb;
-                       set->crtc->fb = set->fb;
-                       if (!drm_crtc_helper_set_mode(set->crtc, set->mode,
-                                                     set->x, set->y,
-                                                     old_fb)) {
-                               DRM_ERROR("failed to set mode on [CRTC:%d]\n",
-                                         set->crtc->base.id);
-                               ret = -EINVAL;
-                               goto fail;
-                       }
-               }
-               drm_helper_disable_unused_functions(dev);
-       } else if (fb_changed) {
-               set->crtc->x = set->x;
-               set->crtc->y = set->y;
-
-               old_fb = set->crtc->fb;
-               if (set->crtc->fb != set->fb)
-                       set->crtc->fb = set->fb;
-               ret = crtc_funcs->mode_set_base(set->crtc,
-                                               set->x, set->y, old_fb);
-               if (ret != 0)
-                       goto fail;
-       }
-       DRM_DEBUG_KMS("Setting connector DPMS state to on\n");
-       for (i = 0; i < set->num_connectors; i++) {
-               DRM_DEBUG_KMS("\t[CONNECTOR:%d:%s] set DPMS on\n", set->connectors[i]->base.id,
-                             drm_get_connector_name(set->connectors[i]));
-               set->connectors[i]->dpms = DRM_MODE_DPMS_ON;
-       }
-
-       kfree(save_connectors);
-       kfree(save_encoders);
-       kfree(save_crtcs);
-       return 0;
-
-fail:
-       /* Restore all previous data. */
-       count = 0;
-       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
-               *crtc = save_crtcs[count++];
-       }
-
-       count = 0;
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-               *encoder = save_encoders[count++];
-       }
-
-       count = 0;
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               *connector = save_connectors[count++];
-       }
-
-       kfree(save_connectors);
-       kfree(save_encoders);
-       kfree(save_crtcs);
-       return ret;
-}
-EXPORT_SYMBOL(drm_crtc_helper_set_config);
-
-static int drm_helper_choose_encoder_dpms(struct drm_encoder *encoder)
-{
-       int dpms = DRM_MODE_DPMS_OFF;
-       struct drm_connector *connector;
-       struct drm_device *dev = encoder->dev;
-
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head)
-               if (connector->encoder == encoder)
-                       if (connector->dpms < dpms)
-                               dpms = connector->dpms;
-       return dpms;
-}
-
-static int drm_helper_choose_crtc_dpms(struct drm_crtc *crtc)
-{
-       int dpms = DRM_MODE_DPMS_OFF;
-       struct drm_connector *connector;
-       struct drm_device *dev = crtc->dev;
-
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head)
-               if (connector->encoder && connector->encoder->crtc == crtc)
-                       if (connector->dpms < dpms)
-                               dpms = connector->dpms;
-       return dpms;
-}
-
-/**
- * drm_helper_connector_dpms
- * @connector affected connector
- * @mode DPMS mode
- *
- * Calls the low-level connector DPMS function, then
- * calls appropriate encoder and crtc DPMS functions as well
- */
-void drm_helper_connector_dpms(struct drm_connector *connector, int mode)
-{
-       struct drm_encoder *encoder = connector->encoder;
-       struct drm_crtc *crtc = encoder ? encoder->crtc : NULL;
-       int old_dpms;
-
-       if (mode == connector->dpms)
-               return;
-
-       old_dpms = connector->dpms;
-       connector->dpms = mode;
-
-       /* from off to on, do crtc then encoder */
-       if (mode < old_dpms) {
-               if (crtc) {
-                       struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
-                       if (crtc_funcs->dpms)
-                               (*crtc_funcs->dpms) (crtc,
-                                                    drm_helper_choose_crtc_dpms(crtc));
-               }
-               if (encoder) {
-                       struct drm_encoder_helper_funcs *encoder_funcs = encoder->helper_private;
-                       if (encoder_funcs->dpms)
-                               (*encoder_funcs->dpms) (encoder,
-                                                       drm_helper_choose_encoder_dpms(encoder));
-               }
-       }
-
-       /* from on to off, do encoder then crtc */
-       if (mode > old_dpms) {
-               if (encoder) {
-                       struct drm_encoder_helper_funcs *encoder_funcs = encoder->helper_private;
-                       if (encoder_funcs->dpms)
-                               (*encoder_funcs->dpms) (encoder,
-                                                       drm_helper_choose_encoder_dpms(encoder));
-               }
-               if (crtc) {
-                       struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
-                       if (crtc_funcs->dpms)
-                               (*crtc_funcs->dpms) (crtc,
-                                                    drm_helper_choose_crtc_dpms(crtc));
-               }
-       }
-
-       return;
-}
-EXPORT_SYMBOL(drm_helper_connector_dpms);
-
-int drm_helper_mode_fill_fb_struct(struct drm_framebuffer *fb,
-                                  struct drm_mode_fb_cmd *mode_cmd)
-{
-       fb->width = mode_cmd->width;
-       fb->height = mode_cmd->height;
-       fb->pitch = mode_cmd->pitch;
-       fb->bits_per_pixel = mode_cmd->bpp;
-       fb->depth = mode_cmd->depth;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_helper_mode_fill_fb_struct);
-
-int drm_helper_resume_force_mode(struct drm_device *dev)
-{
-       struct drm_crtc *crtc;
-       struct drm_encoder *encoder;
-       struct drm_encoder_helper_funcs *encoder_funcs;
-       struct drm_crtc_helper_funcs *crtc_funcs;
-       int ret;
-
-       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
-
-               if (!crtc->enabled)
-                       continue;
-
-               ret = drm_crtc_helper_set_mode(crtc, &crtc->mode,
-                                              crtc->x, crtc->y, crtc->fb);
-
-               if (ret == false)
-                       DRM_ERROR("failed to set mode on crtc %p\n", crtc);
-
-               /* Turn off outputs that were already powered off */
-               if (drm_helper_choose_crtc_dpms(crtc)) {
-                       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-
-                               if(encoder->crtc != crtc)
-                                       continue;
-
-                               encoder_funcs = encoder->helper_private;
-                               if (encoder_funcs->dpms)
-                                       (*encoder_funcs->dpms) (encoder,
-                                                               drm_helper_choose_encoder_dpms(encoder));
-                       }
-
-                       crtc_funcs = crtc->helper_private;
-                       if (crtc_funcs->dpms)
-                               (*crtc_funcs->dpms) (crtc,
-                                                    drm_helper_choose_crtc_dpms(crtc));
-               }
-       }
-       /* disable the unused connectors while restoring the modesetting */
-       drm_helper_disable_unused_functions(dev);
-       return 0;
-}
-EXPORT_SYMBOL(drm_helper_resume_force_mode);
-
-#define DRM_OUTPUT_POLL_PERIOD (10*HZ)
-static void output_poll_execute(struct work_struct *work)
-{
-       struct delayed_work *delayed_work = to_delayed_work(work);
-       struct drm_device *dev = container_of(delayed_work, struct drm_device, mode_config.output_poll_work);
-       struct drm_connector *connector;
-       enum drm_connector_status old_status;
-       bool repoll = false, changed = false;
-
-       if (!drm_kms_helper_poll)
-               return;
-
-       mutex_lock(&dev->mode_config.mutex);
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-
-               /* if this is HPD or polled don't check it -
-                  TV out for instance */
-               if (!connector->polled)
-                       continue;
-
-               else if (connector->polled & (DRM_CONNECTOR_POLL_CONNECT | DRM_CONNECTOR_POLL_DISCONNECT))
-                       repoll = true;
-
-               old_status = connector->status;
-               /* if we are connected and don't want to poll for disconnect
-                  skip it */
-               if (old_status == connector_status_connected &&
-                   !(connector->polled & DRM_CONNECTOR_POLL_DISCONNECT) &&
-                   !(connector->polled & DRM_CONNECTOR_POLL_HPD))
-                       continue;
-
-               connector->status = connector->funcs->detect(connector, false);
-               DRM_DEBUG_KMS("[CONNECTOR:%d:%s] status updated from %d to %d\n",
-                             connector->base.id,
-                             drm_get_connector_name(connector),
-                             old_status, connector->status);
-               if (old_status != connector->status)
-                       changed = true;
-       }
-
-       mutex_unlock(&dev->mode_config.mutex);
-
-       if (changed) {
-               /* send a uevent + call fbdev */
-               drm_sysfs_hotplug_event(dev);
-               if (dev->mode_config.funcs->output_poll_changed)
-                       dev->mode_config.funcs->output_poll_changed(dev);
-       }
-
-       if (repoll)
-               queue_delayed_work(system_nrt_wq, delayed_work, DRM_OUTPUT_POLL_PERIOD);
-}
-
-void drm_kms_helper_poll_disable(struct drm_device *dev)
-{
-       if (!dev->mode_config.poll_enabled)
-               return;
-       cancel_delayed_work_sync(&dev->mode_config.output_poll_work);
-}
-EXPORT_SYMBOL(drm_kms_helper_poll_disable);
-
-void drm_kms_helper_poll_enable(struct drm_device *dev)
-{
-       bool poll = false;
-       struct drm_connector *connector;
-
-       if (!dev->mode_config.poll_enabled || !drm_kms_helper_poll)
-               return;
-
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               if (connector->polled)
-                       poll = true;
-       }
-
-       if (poll)
-               queue_delayed_work(system_nrt_wq, &dev->mode_config.output_poll_work, DRM_OUTPUT_POLL_PERIOD);
-}
-EXPORT_SYMBOL(drm_kms_helper_poll_enable);
-
-void drm_kms_helper_poll_init(struct drm_device *dev)
-{
-       INIT_DELAYED_WORK(&dev->mode_config.output_poll_work, output_poll_execute);
-       dev->mode_config.poll_enabled = true;
-
-       drm_kms_helper_poll_enable(dev);
-}
-EXPORT_SYMBOL(drm_kms_helper_poll_init);
-
-void drm_kms_helper_poll_fini(struct drm_device *dev)
-{
-       drm_kms_helper_poll_disable(dev);
-}
-EXPORT_SYMBOL(drm_kms_helper_poll_fini);
-
-void drm_helper_hpd_irq_event(struct drm_device *dev)
-{
-       if (!dev->mode_config.poll_enabled)
-               return;
-
-       /* kill timer and schedule immediate execution, this doesn't block */
-       cancel_delayed_work(&dev->mode_config.output_poll_work);
-       if (drm_kms_helper_poll)
-               queue_delayed_work(system_nrt_wq, &dev->mode_config.output_poll_work, 0);
-}
-EXPORT_SYMBOL(drm_helper_hpd_irq_event);
diff --git a/services4/3rdparty/linux_drm/drm_debugfs.c b/services4/3rdparty/linux_drm/drm_debugfs.c
deleted file mode 100644 (file)
index 9d8c892..0000000
+++ /dev/null
@@ -1,236 +0,0 @@
-/**
- * \file drm_debugfs.c
- * debugfs support for DRM
- *
- * \author Ben Gamari <bgamari@gmail.com>
- */
-
-/*
- * Created: Sun Dec 21 13:08:50 2008 by bgamari@gmail.com
- *
- * Copyright 2008 Ben Gamari <bgamari@gmail.com>
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/debugfs.h>
-#include <linux/seq_file.h>
-#include <linux/slab.h>
-#include "drmP.h"
-
-#if defined(CONFIG_DEBUG_FS)
-
-/***************************************************
- * Initialization, etc.
- **************************************************/
-
-static struct drm_info_list drm_debugfs_list[] = {
-       {"name", drm_name_info, 0},
-       {"vm", drm_vm_info, 0},
-       {"clients", drm_clients_info, 0},
-       {"queues", drm_queues_info, 0},
-       {"bufs", drm_bufs_info, 0},
-       {"gem_names", drm_gem_name_info, DRIVER_GEM},
-#if DRM_DEBUG_CODE
-       {"vma", drm_vma_info, 0},
-#endif
-};
-#define DRM_DEBUGFS_ENTRIES ARRAY_SIZE(drm_debugfs_list)
-
-
-static int drm_debugfs_open(struct inode *inode, struct file *file)
-{
-       struct drm_info_node *node = inode->i_private;
-
-       return single_open(file, node->info_ent->show, node);
-}
-
-
-static const struct file_operations drm_debugfs_fops = {
-       .owner = THIS_MODULE,
-       .open = drm_debugfs_open,
-       .read = seq_read,
-       .llseek = seq_lseek,
-       .release = single_release,
-};
-
-
-/**
- * Initialize a given set of debugfs files for a device
- *
- * \param files The array of files to create
- * \param count The number of files given
- * \param root DRI debugfs dir entry.
- * \param minor device minor number
- * \return Zero on success, non-zero on failure
- *
- * Create a given set of debugfs files represented by an array of
- * gdm_debugfs_lists in the given root directory.
- */
-int drm_debugfs_create_files(struct drm_info_list *files, int count,
-                            struct dentry *root, struct drm_minor *minor)
-{
-       struct drm_device *dev = minor->dev;
-       struct dentry *ent;
-       struct drm_info_node *tmp;
-       char name[64];
-       int i, ret;
-
-       for (i = 0; i < count; i++) {
-               u32 features = files[i].driver_features;
-
-               if (features != 0 &&
-                   (dev->driver->driver_features & features) != features)
-                       continue;
-
-               tmp = kmalloc(sizeof(struct drm_info_node), GFP_KERNEL);
-               if (tmp == NULL) {
-                       ret = -1;
-                       goto fail;
-               }
-               ent = debugfs_create_file(files[i].name, S_IFREG | S_IRUGO,
-                                         root, tmp, &drm_debugfs_fops);
-               if (!ent) {
-                       DRM_ERROR("Cannot create /sys/kernel/debug/dri/%s/%s\n",
-                                 name, files[i].name);
-                       kfree(tmp);
-                       ret = -1;
-                       goto fail;
-               }
-
-               tmp->minor = minor;
-               tmp->dent = ent;
-               tmp->info_ent = &files[i];
-               list_add(&(tmp->list), &(minor->debugfs_nodes.list));
-       }
-       return 0;
-
-fail:
-       drm_debugfs_remove_files(files, count, minor);
-       return ret;
-}
-EXPORT_SYMBOL(drm_debugfs_create_files);
-
-/**
- * Initialize the DRI debugfs filesystem for a device
- *
- * \param dev DRM device
- * \param minor device minor number
- * \param root DRI debugfs dir entry.
- *
- * Create the DRI debugfs root entry "/sys/kernel/debug/dri", the device debugfs root entry
- * "/sys/kernel/debug/dri/%minor%/", and each entry in debugfs_list as
- * "/sys/kernel/debug/dri/%minor%/%name%".
- */
-int drm_debugfs_init(struct drm_minor *minor, int minor_id,
-                    struct dentry *root)
-{
-       struct drm_device *dev = minor->dev;
-       char name[64];
-       int ret;
-
-       INIT_LIST_HEAD(&minor->debugfs_nodes.list);
-       sprintf(name, "%d", minor_id);
-       minor->debugfs_root = debugfs_create_dir(name, root);
-       if (!minor->debugfs_root) {
-               DRM_ERROR("Cannot create /sys/kernel/debug/dri/%s\n", name);
-               return -1;
-       }
-
-       ret = drm_debugfs_create_files(drm_debugfs_list, DRM_DEBUGFS_ENTRIES,
-                                      minor->debugfs_root, minor);
-       if (ret) {
-               debugfs_remove(minor->debugfs_root);
-               minor->debugfs_root = NULL;
-               DRM_ERROR("Failed to create core drm debugfs files\n");
-               return ret;
-       }
-
-       if (dev->driver->debugfs_init) {
-               ret = dev->driver->debugfs_init(minor);
-               if (ret) {
-                       DRM_ERROR("DRM: Driver failed to initialize "
-                                 "/sys/kernel/debug/dri.\n");
-                       return ret;
-               }
-       }
-       return 0;
-}
-
-
-/**
- * Remove a list of debugfs files
- *
- * \param files The list of files
- * \param count The number of files
- * \param minor The minor of which we should remove the files
- * \return always zero.
- *
- * Remove all debugfs entries created by debugfs_init().
- */
-int drm_debugfs_remove_files(struct drm_info_list *files, int count,
-                            struct drm_minor *minor)
-{
-       struct list_head *pos, *q;
-       struct drm_info_node *tmp;
-       int i;
-
-       for (i = 0; i < count; i++) {
-               list_for_each_safe(pos, q, &minor->debugfs_nodes.list) {
-                       tmp = list_entry(pos, struct drm_info_node, list);
-                       if (tmp->info_ent == &files[i]) {
-                               debugfs_remove(tmp->dent);
-                               list_del(pos);
-                               kfree(tmp);
-                       }
-               }
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_debugfs_remove_files);
-
-/**
- * Cleanup the debugfs filesystem resources.
- *
- * \param minor device minor number.
- * \return always zero.
- *
- * Remove all debugfs entries created by debugfs_init().
- */
-int drm_debugfs_cleanup(struct drm_minor *minor)
-{
-       struct drm_device *dev = minor->dev;
-
-       if (!minor->debugfs_root)
-               return 0;
-
-       if (dev->driver->debugfs_cleanup)
-               dev->driver->debugfs_cleanup(minor);
-
-       drm_debugfs_remove_files(drm_debugfs_list, DRM_DEBUGFS_ENTRIES, minor);
-
-       debugfs_remove(minor->debugfs_root);
-       minor->debugfs_root = NULL;
-
-       return 0;
-}
-
-#endif /* CONFIG_DEBUG_FS */
-
diff --git a/services4/3rdparty/linux_drm/drm_dma.c b/services4/3rdparty/linux_drm/drm_dma.c
deleted file mode 100644 (file)
index 252cbd7..0000000
+++ /dev/null
@@ -1,161 +0,0 @@
-/**
- * \file drm_dma.c
- * DMA IOCTL and function support
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Fri Mar 19 14:30:16 1999 by faith@valinux.com
- *
- * Copyright 1999, 2000 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-
-/**
- * Initialize the DMA data.
- *
- * \param dev DRM device.
- * \return zero on success or a negative value on failure.
- *
- * Allocate and initialize a drm_device_dma structure.
- */
-int drm_dma_setup(struct drm_device *dev)
-{
-       int i;
-
-       dev->dma = kzalloc(sizeof(*dev->dma), GFP_KERNEL);
-       if (!dev->dma)
-               return -ENOMEM;
-
-       for (i = 0; i <= DRM_MAX_ORDER; i++)
-               memset(&dev->dma->bufs[i], 0, sizeof(dev->dma->bufs[0]));
-
-       return 0;
-}
-
-/**
- * Cleanup the DMA resources.
- *
- * \param dev DRM device.
- *
- * Free all pages associated with DMA buffers, the buffers and pages lists, and
- * finally the drm_device::dma structure itself.
- */
-void drm_dma_takedown(struct drm_device *dev)
-{
-       struct drm_device_dma *dma = dev->dma;
-       int i, j;
-
-       if (!dma)
-               return;
-
-       /* Clear dma buffers */
-       for (i = 0; i <= DRM_MAX_ORDER; i++) {
-               if (dma->bufs[i].seg_count) {
-                       DRM_DEBUG("order %d: buf_count = %d,"
-                                 " seg_count = %d\n",
-                                 i,
-                                 dma->bufs[i].buf_count,
-                                 dma->bufs[i].seg_count);
-                       for (j = 0; j < dma->bufs[i].seg_count; j++) {
-                               if (dma->bufs[i].seglist[j]) {
-                                       drm_pci_free(dev, dma->bufs[i].seglist[j]);
-                               }
-                       }
-                       kfree(dma->bufs[i].seglist);
-               }
-               if (dma->bufs[i].buf_count) {
-                       for (j = 0; j < dma->bufs[i].buf_count; j++) {
-                               kfree(dma->bufs[i].buflist[j].dev_private);
-                       }
-                       kfree(dma->bufs[i].buflist);
-               }
-       }
-
-       kfree(dma->buflist);
-       kfree(dma->pagelist);
-       kfree(dev->dma);
-       dev->dma = NULL;
-}
-
-/**
- * Free a buffer.
- *
- * \param dev DRM device.
- * \param buf buffer to free.
- *
- * Resets the fields of \p buf.
- */
-void drm_free_buffer(struct drm_device *dev, struct drm_buf * buf)
-{
-       if (!buf)
-               return;
-
-       buf->waiting = 0;
-       buf->pending = 0;
-       buf->file_priv = NULL;
-       buf->used = 0;
-
-       if (drm_core_check_feature(dev, DRIVER_DMA_QUEUE)
-           && waitqueue_active(&buf->dma_wait)) {
-               wake_up_interruptible(&buf->dma_wait);
-       }
-}
-
-/**
- * Reclaim the buffers.
- *
- * \param file_priv DRM file private.
- *
- * Frees each buffer associated with \p file_priv not already on the hardware.
- */
-void drm_core_reclaim_buffers(struct drm_device *dev,
-                             struct drm_file *file_priv)
-{
-       struct drm_device_dma *dma = dev->dma;
-       int i;
-
-       if (!dma)
-               return;
-       for (i = 0; i < dma->buf_count; i++) {
-               if (dma->buflist[i]->file_priv == file_priv) {
-                       switch (dma->buflist[i]->list) {
-                       case DRM_LIST_NONE:
-                               drm_free_buffer(dev, dma->buflist[i]);
-                               break;
-                       case DRM_LIST_WAIT:
-                               dma->buflist[i]->list = DRM_LIST_RECLAIM;
-                               break;
-                       default:
-                               /* Buffer already on hardware. */
-                               break;
-                       }
-               }
-       }
-}
-
-EXPORT_SYMBOL(drm_core_reclaim_buffers);
diff --git a/services4/3rdparty/linux_drm/drm_dp_i2c_helper.c b/services4/3rdparty/linux_drm/drm_dp_i2c_helper.c
deleted file mode 100644 (file)
index f7eba0a..0000000
+++ /dev/null
@@ -1,208 +0,0 @@
-/*
- * Copyright Â© 2009 Keith Packard
- *
- * Permission to use, copy, modify, distribute, and sell this software and its
- * documentation for any purpose is hereby granted without fee, provided that
- * the above copyright notice appear in all copies and that both that copyright
- * notice and this permission notice appear in supporting documentation, and
- * that the name of the copyright holders not be used in advertising or
- * publicity pertaining to distribution of the software without specific,
- * written prior permission.  The copyright holders make no representations
- * about the suitability of this software for any purpose.  It is provided "as
- * is" without express or implied warranty.
- *
- * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
- * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
- * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
- * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
- * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
- * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
- * OF THIS SOFTWARE.
- */
-
-#include <linux/kernel.h>
-#include <linux/module.h>
-#include <linux/delay.h>
-#include <linux/init.h>
-#include <linux/errno.h>
-#include <linux/sched.h>
-#include <linux/i2c.h>
-#include "drm_dp_helper.h"
-#include "drmP.h"
-
-/* Run a single AUX_CH I2C transaction, writing/reading data as necessary */
-static int
-i2c_algo_dp_aux_transaction(struct i2c_adapter *adapter, int mode,
-                           uint8_t write_byte, uint8_t *read_byte)
-{
-       struct i2c_algo_dp_aux_data *algo_data = adapter->algo_data;
-       int ret;
-       
-       ret = (*algo_data->aux_ch)(adapter, mode,
-                                  write_byte, read_byte);
-       return ret;
-}
-
-/*
- * I2C over AUX CH
- */
-
-/*
- * Send the address. If the I2C link is running, this 'restarts'
- * the connection with the new address, this is used for doing
- * a write followed by a read (as needed for DDC)
- */
-static int
-i2c_algo_dp_aux_address(struct i2c_adapter *adapter, u16 address, bool reading)
-{
-       struct i2c_algo_dp_aux_data *algo_data = adapter->algo_data;
-       int mode = MODE_I2C_START;
-       int ret;
-
-       if (reading)
-               mode |= MODE_I2C_READ;
-       else
-               mode |= MODE_I2C_WRITE;
-       algo_data->address = address;
-       algo_data->running = true;
-       ret = i2c_algo_dp_aux_transaction(adapter, mode, 0, NULL);
-       return ret;
-}
-
-/*
- * Stop the I2C transaction. This closes out the link, sending
- * a bare address packet with the MOT bit turned off
- */
-static void
-i2c_algo_dp_aux_stop(struct i2c_adapter *adapter, bool reading)
-{
-       struct i2c_algo_dp_aux_data *algo_data = adapter->algo_data;
-       int mode = MODE_I2C_STOP;
-
-       if (reading)
-               mode |= MODE_I2C_READ;
-       else
-               mode |= MODE_I2C_WRITE;
-       if (algo_data->running) {
-               (void) i2c_algo_dp_aux_transaction(adapter, mode, 0, NULL);
-               algo_data->running = false;
-       }
-}
-
-/*
- * Write a single byte to the current I2C address, the
- * the I2C link must be running or this returns -EIO
- */
-static int
-i2c_algo_dp_aux_put_byte(struct i2c_adapter *adapter, u8 byte)
-{
-       struct i2c_algo_dp_aux_data *algo_data = adapter->algo_data;
-       int ret;
-
-       if (!algo_data->running)
-               return -EIO;
-
-       ret = i2c_algo_dp_aux_transaction(adapter, MODE_I2C_WRITE, byte, NULL);
-       return ret;
-}
-
-/*
- * Read a single byte from the current I2C address, the
- * I2C link must be running or this returns -EIO
- */
-static int
-i2c_algo_dp_aux_get_byte(struct i2c_adapter *adapter, u8 *byte_ret)
-{
-       struct i2c_algo_dp_aux_data *algo_data = adapter->algo_data;
-       int ret;
-
-       if (!algo_data->running)
-               return -EIO;
-
-       ret = i2c_algo_dp_aux_transaction(adapter, MODE_I2C_READ, 0, byte_ret);
-       return ret;
-}
-
-static int
-i2c_algo_dp_aux_xfer(struct i2c_adapter *adapter,
-                    struct i2c_msg *msgs,
-                    int num)
-{
-       int ret = 0;
-       bool reading = false;
-       int m;
-       int b;
-
-       for (m = 0; m < num; m++) {
-               u16 len = msgs[m].len;
-               u8 *buf = msgs[m].buf;
-               reading = (msgs[m].flags & I2C_M_RD) != 0;
-               ret = i2c_algo_dp_aux_address(adapter, msgs[m].addr, reading);
-               if (ret < 0)
-                       break;
-               if (reading) {
-                       for (b = 0; b < len; b++) {
-                               ret = i2c_algo_dp_aux_get_byte(adapter, &buf[b]);
-                               if (ret < 0)
-                                       break;
-                       }
-               } else {
-                       for (b = 0; b < len; b++) {
-                               ret = i2c_algo_dp_aux_put_byte(adapter, buf[b]);
-                               if (ret < 0)
-                                       break;
-                       }
-               }
-               if (ret < 0)
-                       break;
-       }
-       if (ret >= 0)
-               ret = num;
-       i2c_algo_dp_aux_stop(adapter, reading);
-       DRM_DEBUG_KMS("dp_aux_xfer return %d\n", ret);
-       return ret;
-}
-
-static u32
-i2c_algo_dp_aux_functionality(struct i2c_adapter *adapter)
-{
-       return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL |
-              I2C_FUNC_SMBUS_READ_BLOCK_DATA |
-              I2C_FUNC_SMBUS_BLOCK_PROC_CALL |
-              I2C_FUNC_10BIT_ADDR;
-}
-
-static const struct i2c_algorithm i2c_dp_aux_algo = {
-       .master_xfer    = i2c_algo_dp_aux_xfer,
-       .functionality  = i2c_algo_dp_aux_functionality,
-};
-
-static void
-i2c_dp_aux_reset_bus(struct i2c_adapter *adapter)
-{
-       (void) i2c_algo_dp_aux_address(adapter, 0, false);
-       (void) i2c_algo_dp_aux_stop(adapter, false);
-                                          
-}
-
-static int
-i2c_dp_aux_prepare_bus(struct i2c_adapter *adapter)
-{
-       adapter->algo = &i2c_dp_aux_algo;
-       adapter->retries = 3;
-       i2c_dp_aux_reset_bus(adapter);
-       return 0;
-}
-
-int
-i2c_dp_aux_add_bus(struct i2c_adapter *adapter)
-{
-       int error;
-       
-       error = i2c_dp_aux_prepare_bus(adapter);
-       if (error)
-               return error;
-       error = i2c_add_adapter(adapter);
-       return error;
-}
-EXPORT_SYMBOL(i2c_dp_aux_add_bus);
diff --git a/services4/3rdparty/linux_drm/drm_drv.c b/services4/3rdparty/linux_drm/drm_drv.c
deleted file mode 100644 (file)
index 271835a..0000000
+++ /dev/null
@@ -1,529 +0,0 @@
-/**
- * \file drm_drv.c
- * Generic driver template
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- *
- * To use this template, you must at least define the following (samples
- * given for the MGA driver):
- *
- * \code
- * #define DRIVER_AUTHOR       "VA Linux Systems, Inc."
- *
- * #define DRIVER_NAME         "mga"
- * #define DRIVER_DESC         "Matrox G200/G400"
- * #define DRIVER_DATE         "20001127"
- *
- * #define drm_x               mga_##x
- * \endcode
- */
-
-/*
- * Created: Thu Nov 23 03:10:50 2000 by gareth@valinux.com
- *
- * Copyright 1999, 2000 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/debugfs.h>
-#include <linux/slab.h>
-#include "drmP.h"
-#include "drm_core.h"
-
-
-static int drm_version(struct drm_device *dev, void *data,
-                      struct drm_file *file_priv);
-
-#define DRM_IOCTL_DEF(ioctl, _func, _flags) \
-       [DRM_IOCTL_NR(ioctl)] = {.cmd = ioctl, .func = _func, .flags = _flags, .cmd_drv = 0}
-
-/** Ioctl table */
-static struct drm_ioctl_desc drm_ioctls[] = {
-       DRM_IOCTL_DEF(DRM_IOCTL_VERSION, drm_version, 0),
-       DRM_IOCTL_DEF(DRM_IOCTL_GET_UNIQUE, drm_getunique, 0),
-       DRM_IOCTL_DEF(DRM_IOCTL_GET_MAGIC, drm_getmagic, 0),
-       DRM_IOCTL_DEF(DRM_IOCTL_IRQ_BUSID, drm_irq_by_busid, DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_GET_MAP, drm_getmap, 0),
-       DRM_IOCTL_DEF(DRM_IOCTL_GET_CLIENT, drm_getclient, 0),
-       DRM_IOCTL_DEF(DRM_IOCTL_GET_STATS, drm_getstats, 0),
-       DRM_IOCTL_DEF(DRM_IOCTL_SET_VERSION, drm_setversion, DRM_MASTER),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_SET_UNIQUE, drm_setunique, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_BLOCK, drm_noop, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_UNBLOCK, drm_noop, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_AUTH_MAGIC, drm_authmagic, DRM_AUTH|DRM_MASTER),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_ADD_MAP, drm_addmap_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_RM_MAP, drm_rmmap_ioctl, DRM_AUTH),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_SET_SAREA_CTX, drm_setsareactx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_GET_SAREA_CTX, drm_getsareactx, DRM_AUTH),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_SET_MASTER, drm_setmaster_ioctl, DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_DROP_MASTER, drm_dropmaster_ioctl, DRM_ROOT_ONLY),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_ADD_CTX, drm_addctx, DRM_AUTH|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_RM_CTX, drm_rmctx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_MOD_CTX, drm_modctx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_GET_CTX, drm_getctx, DRM_AUTH),
-       DRM_IOCTL_DEF(DRM_IOCTL_SWITCH_CTX, drm_switchctx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_NEW_CTX, drm_newctx, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_RES_CTX, drm_resctx, DRM_AUTH),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_ADD_DRAW, drm_noop, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_RM_DRAW, drm_noop, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_LOCK, drm_lock, DRM_AUTH),
-       DRM_IOCTL_DEF(DRM_IOCTL_UNLOCK, drm_unlock, DRM_AUTH),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_FINISH, drm_noop, DRM_AUTH),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_ADD_BUFS, drm_addbufs, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_MARK_BUFS, drm_markbufs, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_INFO_BUFS, drm_infobufs, DRM_AUTH),
-       DRM_IOCTL_DEF(DRM_IOCTL_MAP_BUFS, drm_mapbufs, DRM_AUTH),
-       DRM_IOCTL_DEF(DRM_IOCTL_FREE_BUFS, drm_freebufs, DRM_AUTH),
-       /* The DRM_IOCTL_DMA ioctl should be defined by the driver. */
-       DRM_IOCTL_DEF(DRM_IOCTL_DMA, NULL, DRM_AUTH),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_CONTROL, drm_control, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-
-#if __OS_HAS_AGP
-       DRM_IOCTL_DEF(DRM_IOCTL_AGP_ACQUIRE, drm_agp_acquire_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_AGP_RELEASE, drm_agp_release_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_AGP_ENABLE, drm_agp_enable_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_AGP_INFO, drm_agp_info_ioctl, DRM_AUTH),
-       DRM_IOCTL_DEF(DRM_IOCTL_AGP_ALLOC, drm_agp_alloc_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_AGP_FREE, drm_agp_free_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_AGP_BIND, drm_agp_bind_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_AGP_UNBIND, drm_agp_unbind_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-#endif
-
-       DRM_IOCTL_DEF(DRM_IOCTL_SG_ALLOC, drm_sg_alloc_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-       DRM_IOCTL_DEF(DRM_IOCTL_SG_FREE, drm_sg_free, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_WAIT_VBLANK, drm_wait_vblank, 0),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_MODESET_CTL, drm_modeset_ctl, 0),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_UPDATE_DRAW, drm_noop, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_GEM_CLOSE, drm_gem_close_ioctl, DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_GEM_FLINK, drm_gem_flink_ioctl, DRM_AUTH|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_GEM_OPEN, drm_gem_open_ioctl, DRM_AUTH|DRM_UNLOCKED),
-
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_GETRESOURCES, drm_mode_getresources, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_GETCRTC, drm_mode_getcrtc, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_SETCRTC, drm_mode_setcrtc, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_CURSOR, drm_mode_cursor_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_GETGAMMA, drm_mode_gamma_get_ioctl, DRM_MASTER|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_SETGAMMA, drm_mode_gamma_set_ioctl, DRM_MASTER|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_GETENCODER, drm_mode_getencoder, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_GETCONNECTOR, drm_mode_getconnector, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_ATTACHMODE, drm_mode_attachmode_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_DETACHMODE, drm_mode_detachmode_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_GETPROPERTY, drm_mode_getproperty_ioctl, DRM_MASTER | DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_SETPROPERTY, drm_mode_connector_property_set_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_GETPROPBLOB, drm_mode_getblob_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_GETFB, drm_mode_getfb, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_ADDFB, drm_mode_addfb, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_RMFB, drm_mode_rmfb, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_PAGE_FLIP, drm_mode_page_flip_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
-       DRM_IOCTL_DEF(DRM_IOCTL_MODE_DIRTYFB, drm_mode_dirtyfb_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED)
-};
-
-#define DRM_CORE_IOCTL_COUNT   ARRAY_SIZE( drm_ioctls )
-
-/**
- * Take down the DRM device.
- *
- * \param dev DRM device structure.
- *
- * Frees every resource in \p dev.
- *
- * \sa drm_device
- */
-int drm_lastclose(struct drm_device * dev)
-{
-       struct drm_vma_entry *vma, *vma_temp;
-       int i;
-
-       DRM_DEBUG("\n");
-
-       if (dev->driver->lastclose)
-               dev->driver->lastclose(dev);
-       DRM_DEBUG("driver lastclose completed\n");
-
-       if (dev->irq_enabled && !drm_core_check_feature(dev, DRIVER_MODESET))
-               drm_irq_uninstall(dev);
-
-       mutex_lock(&dev->struct_mutex);
-
-       /* Clear AGP information */
-       if (drm_core_has_AGP(dev) && dev->agp &&
-                       !drm_core_check_feature(dev, DRIVER_MODESET)) {
-               struct drm_agp_mem *entry, *tempe;
-
-               /* Remove AGP resources, but leave dev->agp
-                  intact until drv_cleanup is called. */
-               list_for_each_entry_safe(entry, tempe, &dev->agp->memory, head) {
-                       if (entry->bound)
-                               drm_unbind_agp(entry->memory);
-                       drm_free_agp(entry->memory, entry->pages);
-                       kfree(entry);
-               }
-               INIT_LIST_HEAD(&dev->agp->memory);
-
-               if (dev->agp->acquired)
-                       drm_agp_release(dev);
-
-               dev->agp->acquired = 0;
-               dev->agp->enabled = 0;
-       }
-       if (drm_core_check_feature(dev, DRIVER_SG) && dev->sg &&
-           !drm_core_check_feature(dev, DRIVER_MODESET)) {
-               drm_sg_cleanup(dev->sg);
-               dev->sg = NULL;
-       }
-
-       /* Clear vma list (only built for debugging) */
-       list_for_each_entry_safe(vma, vma_temp, &dev->vmalist, head) {
-               list_del(&vma->head);
-               kfree(vma);
-       }
-
-       if (drm_core_check_feature(dev, DRIVER_DMA_QUEUE) && dev->queuelist) {
-               for (i = 0; i < dev->queue_count; i++) {
-                       kfree(dev->queuelist[i]);
-                       dev->queuelist[i] = NULL;
-               }
-               kfree(dev->queuelist);
-               dev->queuelist = NULL;
-       }
-       dev->queue_count = 0;
-
-       if (drm_core_check_feature(dev, DRIVER_HAVE_DMA) &&
-           !drm_core_check_feature(dev, DRIVER_MODESET))
-               drm_dma_takedown(dev);
-
-       dev->dev_mapping = NULL;
-       mutex_unlock(&dev->struct_mutex);
-
-       DRM_DEBUG("lastclose completed\n");
-       return 0;
-}
-
-/**
- * Module initialization. Called via init_module at module load time, or via
- * linux/init/main.c (this is not currently supported).
- *
- * \return zero on success or a negative number on failure.
- *
- * Initializes an array of drm_device structures, and attempts to
- * initialize all available devices, using consecutive minors, registering the
- * stubs and initializing the device.
- *
- * Expands the \c DRIVER_PREINIT and \c DRIVER_POST_INIT macros before and
- * after the initialization for driver customization.
- */
-int drm_init(struct drm_driver *driver)
-{
-       DRM_DEBUG("\n");
-       INIT_LIST_HEAD(&driver->device_list);
-
-       if (driver->driver_features & DRIVER_USE_PLATFORM_DEVICE)
-               return drm_platform_init(driver);
-       else
-               return drm_pci_init(driver);
-}
-
-EXPORT_SYMBOL(drm_init);
-
-void drm_exit(struct drm_driver *driver)
-{
-       struct drm_device *dev, *tmp;
-       DRM_DEBUG("\n");
-
-       if (driver->driver_features & DRIVER_MODESET) {
-               pci_unregister_driver(&driver->pci_driver);
-       } else {
-               list_for_each_entry_safe(dev, tmp, &driver->device_list, driver_item)
-                       drm_put_dev(dev);
-       }
-
-       DRM_INFO("Module unloaded\n");
-}
-
-EXPORT_SYMBOL(drm_exit);
-
-/** File operations structure */
-static const struct file_operations drm_stub_fops = {
-       .owner = THIS_MODULE,
-       .open = drm_stub_open,
-       .llseek = noop_llseek,
-};
-
-static int __init drm_core_init(void)
-{
-       int ret = -ENOMEM;
-
-       drm_global_init();
-       idr_init(&drm_minors_idr);
-
-       if (register_chrdev(DRM_MAJOR, "drm", &drm_stub_fops))
-               goto err_p1;
-
-       drm_class = drm_sysfs_create(THIS_MODULE, "drm");
-       if (IS_ERR(drm_class)) {
-               printk(KERN_ERR "DRM: Error creating drm class.\n");
-               ret = PTR_ERR(drm_class);
-               goto err_p2;
-       }
-
-       drm_proc_root = proc_mkdir("dri", NULL);
-       if (!drm_proc_root) {
-               DRM_ERROR("Cannot create /proc/dri\n");
-               ret = -1;
-               goto err_p3;
-       }
-
-       drm_debugfs_root = debugfs_create_dir("dri", NULL);
-       if (!drm_debugfs_root) {
-               DRM_ERROR("Cannot create /sys/kernel/debug/dri\n");
-               ret = -1;
-               goto err_p3;
-       }
-
-       DRM_INFO("Initialized %s %d.%d.%d %s\n",
-                CORE_NAME, CORE_MAJOR, CORE_MINOR, CORE_PATCHLEVEL, CORE_DATE);
-       return 0;
-err_p3:
-       drm_sysfs_destroy();
-err_p2:
-       unregister_chrdev(DRM_MAJOR, "drm");
-
-       idr_destroy(&drm_minors_idr);
-err_p1:
-       return ret;
-}
-
-static void __exit drm_core_exit(void)
-{
-       remove_proc_entry("dri", NULL);
-       debugfs_remove(drm_debugfs_root);
-       drm_sysfs_destroy();
-
-       unregister_chrdev(DRM_MAJOR, "drm");
-
-       idr_remove_all(&drm_minors_idr);
-       idr_destroy(&drm_minors_idr);
-}
-
-module_init(drm_core_init);
-module_exit(drm_core_exit);
-
-/**
- * Copy and IOCTL return string to user space
- */
-static int drm_copy_field(char *buf, size_t *buf_len, const char *value)
-{
-       int len;
-
-       /* don't overflow userbuf */
-       len = strlen(value);
-       if (len > *buf_len)
-               len = *buf_len;
-
-       /* let userspace know exact length of driver value (which could be
-        * larger than the userspace-supplied buffer) */
-       *buf_len = strlen(value);
-
-       /* finally, try filling in the userbuf */
-       if (len && buf)
-               if (copy_to_user(buf, value, len))
-                       return -EFAULT;
-       return 0;
-}
-
-/**
- * Get version information
- *
- * \param inode device inode.
- * \param filp file pointer.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_version structure.
- * \return zero on success or negative number on failure.
- *
- * Fills in the version information in \p arg.
- */
-static int drm_version(struct drm_device *dev, void *data,
-                      struct drm_file *file_priv)
-{
-       struct drm_version *version = data;
-       int err;
-
-       version->version_major = dev->driver->major;
-       version->version_minor = dev->driver->minor;
-       version->version_patchlevel = dev->driver->patchlevel;
-       err = drm_copy_field(version->name, &version->name_len,
-                       dev->driver->name);
-       if (!err)
-               err = drm_copy_field(version->date, &version->date_len,
-                               dev->driver->date);
-       if (!err)
-               err = drm_copy_field(version->desc, &version->desc_len,
-                               dev->driver->desc);
-
-       return err;
-}
-
-/**
- * Called whenever a process performs an ioctl on /dev/drm.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument.
- * \return zero on success or negative number on failure.
- *
- * Looks up the ioctl function in the ::ioctls table, checking for root
- * previleges if so required, and dispatches to the respective function.
- */
-long drm_ioctl(struct file *filp,
-             unsigned int cmd, unsigned long arg)
-{
-       struct drm_file *file_priv = filp->private_data;
-       struct drm_device *dev;
-       struct drm_ioctl_desc *ioctl;
-       drm_ioctl_t *func;
-       unsigned int nr = DRM_IOCTL_NR(cmd);
-       int retcode = -EINVAL;
-       char stack_kdata[128];
-       char *kdata = NULL;
-       unsigned int usize, asize;
-
-       dev = file_priv->minor->dev;
-       atomic_inc(&dev->ioctl_count);
-       atomic_inc(&dev->counts[_DRM_STAT_IOCTLS]);
-       ++file_priv->ioctl_count;
-
-       DRM_DEBUG("pid=%d, cmd=0x%02x, nr=0x%02x, dev 0x%lx, auth=%d\n",
-                 task_pid_nr(current), cmd, nr,
-                 (long)old_encode_dev(file_priv->minor->device),
-                 file_priv->authenticated);
-
-       if ((nr >= DRM_CORE_IOCTL_COUNT) &&
-           ((nr < DRM_COMMAND_BASE) || (nr >= DRM_COMMAND_END)))
-               goto err_i1;
-       if ((nr >= DRM_COMMAND_BASE) && (nr < DRM_COMMAND_END) &&
-           (nr < DRM_COMMAND_BASE + dev->driver->num_ioctls)) {
-               u32 drv_size;
-               ioctl = &dev->driver->ioctls[nr - DRM_COMMAND_BASE];
-               drv_size = _IOC_SIZE(ioctl->cmd_drv);
-               usize = asize = _IOC_SIZE(cmd);
-               if (drv_size > asize)
-                       asize = drv_size;
-       }
-       else if ((nr >= DRM_COMMAND_END) || (nr < DRM_COMMAND_BASE)) {
-               ioctl = &drm_ioctls[nr];
-               cmd = ioctl->cmd;
-               usize = asize = _IOC_SIZE(cmd);
-       } else
-               goto err_i1;
-
-       /* Do not trust userspace, use our own definition */
-       func = ioctl->func;
-       /* is there a local override? */
-       if ((nr == DRM_IOCTL_NR(DRM_IOCTL_DMA)) && dev->driver->dma_ioctl)
-               func = dev->driver->dma_ioctl;
-
-       if (!func) {
-               DRM_DEBUG("no function\n");
-               retcode = -EINVAL;
-       } else if (((ioctl->flags & DRM_ROOT_ONLY) && !capable(CAP_SYS_ADMIN)) ||
-                  ((ioctl->flags & DRM_AUTH) && !file_priv->authenticated) ||
-                  ((ioctl->flags & DRM_MASTER) && !file_priv->is_master) ||
-                  (!(ioctl->flags & DRM_CONTROL_ALLOW) && (file_priv->minor->type == DRM_MINOR_CONTROL))) {
-               retcode = -EACCES;
-       } else {
-               if (cmd & (IOC_IN | IOC_OUT)) {
-                       if (asize <= sizeof(stack_kdata)) {
-                               kdata = stack_kdata;
-                       } else {
-                               kdata = kmalloc(asize, GFP_KERNEL);
-                               if (!kdata) {
-                                       retcode = -ENOMEM;
-                                       goto err_i1;
-                               }
-                       }
-               }
-
-               if (cmd & IOC_IN) {
-                       if (copy_from_user(kdata, (void __user *)arg,
-                                          usize) != 0) {
-                               retcode = -EFAULT;
-                               goto err_i1;
-                       }
-               } else
-                       memset(kdata, 0, usize);
-
-               if (ioctl->flags & DRM_UNLOCKED)
-                       retcode = func(dev, kdata, file_priv);
-               else {
-                       mutex_lock(&drm_global_mutex);
-                       retcode = func(dev, kdata, file_priv);
-                       mutex_unlock(&drm_global_mutex);
-               }
-
-               if (cmd & IOC_OUT) {
-                       if (copy_to_user((void __user *)arg, kdata,
-                                        usize) != 0)
-                               retcode = -EFAULT;
-               }
-       }
-
-      err_i1:
-       if (kdata != stack_kdata)
-               kfree(kdata);
-       atomic_dec(&dev->ioctl_count);
-       if (retcode)
-               DRM_DEBUG("ret = %x\n", retcode);
-       return retcode;
-}
-
-EXPORT_SYMBOL(drm_ioctl);
-
-struct drm_local_map *drm_getsarea(struct drm_device *dev)
-{
-       struct drm_map_list *entry;
-
-       list_for_each_entry(entry, &dev->maplist, head) {
-               if (entry->map && entry->map->type == _DRM_SHM &&
-                   (entry->map->flags & _DRM_CONTAINS_LOCK)) {
-                       return entry->map;
-               }
-       }
-       return NULL;
-}
-EXPORT_SYMBOL(drm_getsarea);
diff --git a/services4/3rdparty/linux_drm/drm_edid.c b/services4/3rdparty/linux_drm/drm_edid.c
deleted file mode 100644 (file)
index a245d17..0000000
+++ /dev/null
@@ -1,1506 +0,0 @@
-/*
- * Copyright (c) 2006 Luc Verhaegen (quirks list)
- * Copyright (c) 2007-2008 Intel Corporation
- *   Jesse Barnes <jesse.barnes@intel.com>
- * Copyright 2010 Red Hat, Inc.
- *
- * DDC probing routines (drm_ddc_read & drm_do_probe_ddc_edid) originally from
- * FB layer.
- *   Copyright (C) 2006 Dennis Munsie <dmunsie@cecropia.com>
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sub license,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the
- * next paragraph) shall be included in all copies or substantial portions
- * of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
- * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- */
-#include <linux/kernel.h>
-#include <linux/slab.h>
-#include <linux/i2c.h>
-#include "drmP.h"
-#include "drm_edid.h"
-#include "drm_edid_modes.h"
-
-#define version_greater(edid, maj, min) \
-       (((edid)->version > (maj)) || \
-        ((edid)->version == (maj) && (edid)->revision > (min)))
-
-#define EDID_EST_TIMINGS 16
-#define EDID_STD_TIMINGS 8
-#define EDID_DETAILED_TIMINGS 4
-
-/*
- * EDID blocks out in the wild have a variety of bugs, try to collect
- * them here (note that userspace may work around broken monitors first,
- * but fixes should make their way here so that the kernel "just works"
- * on as many displays as possible).
- */
-
-/* First detailed mode wrong, use largest 60Hz mode */
-#define EDID_QUIRK_PREFER_LARGE_60             (1 << 0)
-/* Reported 135MHz pixel clock is too high, needs adjustment */
-#define EDID_QUIRK_135_CLOCK_TOO_HIGH          (1 << 1)
-/* Prefer the largest mode at 75 Hz */
-#define EDID_QUIRK_PREFER_LARGE_75             (1 << 2)
-/* Detail timing is in cm not mm */
-#define EDID_QUIRK_DETAILED_IN_CM              (1 << 3)
-/* Detailed timing descriptors have bogus size values, so just take the
- * maximum size and use that.
- */
-#define EDID_QUIRK_DETAILED_USE_MAXIMUM_SIZE   (1 << 4)
-/* Monitor forgot to set the first detailed is preferred bit. */
-#define EDID_QUIRK_FIRST_DETAILED_PREFERRED    (1 << 5)
-/* use +hsync +vsync for detailed mode */
-#define EDID_QUIRK_DETAILED_SYNC_PP            (1 << 6)
-
-struct detailed_mode_closure {
-       struct drm_connector *connector;
-       struct edid *edid;
-       bool preferred;
-       u32 quirks;
-       int modes;
-};
-
-#define LEVEL_DMT      0
-#define LEVEL_GTF      1
-#define LEVEL_GTF2     2
-#define LEVEL_CVT      3
-
-static struct edid_quirk {
-       char *vendor;
-       int product_id;
-       u32 quirks;
-} edid_quirk_list[] = {
-       /* Acer AL1706 */
-       { "ACR", 44358, EDID_QUIRK_PREFER_LARGE_60 },
-       /* Acer F51 */
-       { "API", 0x7602, EDID_QUIRK_PREFER_LARGE_60 },
-       /* Unknown Acer */
-       { "ACR", 2423, EDID_QUIRK_FIRST_DETAILED_PREFERRED },
-
-       /* Belinea 10 15 55 */
-       { "MAX", 1516, EDID_QUIRK_PREFER_LARGE_60 },
-       { "MAX", 0x77e, EDID_QUIRK_PREFER_LARGE_60 },
-
-       /* Envision Peripherals, Inc. EN-7100e */
-       { "EPI", 59264, EDID_QUIRK_135_CLOCK_TOO_HIGH },
-       /* Envision EN2028 */
-       { "EPI", 8232, EDID_QUIRK_PREFER_LARGE_60 },
-
-       /* Funai Electronics PM36B */
-       { "FCM", 13600, EDID_QUIRK_PREFER_LARGE_75 |
-         EDID_QUIRK_DETAILED_IN_CM },
-
-       /* LG Philips LCD LP154W01-A5 */
-       { "LPL", 0, EDID_QUIRK_DETAILED_USE_MAXIMUM_SIZE },
-       { "LPL", 0x2a00, EDID_QUIRK_DETAILED_USE_MAXIMUM_SIZE },
-
-       /* Philips 107p5 CRT */
-       { "PHL", 57364, EDID_QUIRK_FIRST_DETAILED_PREFERRED },
-
-       /* Proview AY765C */
-       { "PTS", 765, EDID_QUIRK_FIRST_DETAILED_PREFERRED },
-
-       /* Samsung SyncMaster 205BW.  Note: irony */
-       { "SAM", 541, EDID_QUIRK_DETAILED_SYNC_PP },
-       /* Samsung SyncMaster 22[5-6]BW */
-       { "SAM", 596, EDID_QUIRK_PREFER_LARGE_60 },
-       { "SAM", 638, EDID_QUIRK_PREFER_LARGE_60 },
-};
-
-/*** DDC fetch and block validation ***/
-
-static const u8 edid_header[] = {
-       0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00
-};
-
-/*
- * Sanity check the EDID block (base or extension).  Return 0 if the block
- * doesn't check out, or 1 if it's valid.
- */
-static bool
-drm_edid_block_valid(u8 *raw_edid)
-{
-       int i;
-       u8 csum = 0;
-       struct edid *edid = (struct edid *)raw_edid;
-
-       if (raw_edid[0] == 0x00) {
-               int score = 0;
-
-               for (i = 0; i < sizeof(edid_header); i++)
-                       if (raw_edid[i] == edid_header[i])
-                               score++;
-
-               if (score == 8) ;
-               else if (score >= 6) {
-                       DRM_DEBUG("Fixing EDID header, your hardware may be failing\n");
-                       memcpy(raw_edid, edid_header, sizeof(edid_header));
-               } else {
-                       goto bad;
-               }
-       }
-
-       for (i = 0; i < EDID_LENGTH; i++)
-               csum += raw_edid[i];
-       if (csum) {
-               DRM_ERROR("EDID checksum is invalid, remainder is %d\n", csum);
-
-               /* allow CEA to slide through, switches mangle this */
-               if (raw_edid[0] != 0x02)
-                       goto bad;
-       }
-
-       /* per-block-type checks */
-       switch (raw_edid[0]) {
-       case 0: /* base */
-               if (edid->version != 1) {
-                       DRM_ERROR("EDID has major version %d, instead of 1\n", edid->version);
-                       goto bad;
-               }
-
-               if (edid->revision > 4)
-                       DRM_DEBUG("EDID minor > 4, assuming backward compatibility\n");
-               break;
-
-       default:
-               break;
-       }
-
-       return 1;
-
-bad:
-       if (raw_edid) {
-               DRM_ERROR("Raw EDID:\n");
-               print_hex_dump_bytes(KERN_ERR, DUMP_PREFIX_NONE, raw_edid, EDID_LENGTH);
-               printk("\n");
-       }
-       return 0;
-}
-
-/**
- * drm_edid_is_valid - sanity check EDID data
- * @edid: EDID data
- *
- * Sanity-check an entire EDID record (including extensions)
- */
-bool drm_edid_is_valid(struct edid *edid)
-{
-       int i;
-       u8 *raw = (u8 *)edid;
-
-       if (!edid)
-               return false;
-
-       for (i = 0; i <= edid->extensions; i++)
-               if (!drm_edid_block_valid(raw + i * EDID_LENGTH))
-                       return false;
-
-       return true;
-}
-EXPORT_SYMBOL(drm_edid_is_valid);
-
-#define DDC_ADDR 0x50
-#define DDC_SEGMENT_ADDR 0x30
-/**
- * Get EDID information via I2C.
- *
- * \param adapter : i2c device adaptor
- * \param buf     : EDID data buffer to be filled
- * \param len     : EDID data buffer length
- * \return 0 on success or -1 on failure.
- *
- * Try to fetch EDID information by calling i2c driver function.
- */
-static int
-drm_do_probe_ddc_edid(struct i2c_adapter *adapter, unsigned char *buf,
-                     int block, int len)
-{
-       unsigned char start = block * EDID_LENGTH;
-       struct i2c_msg msgs[] = {
-               {
-                       .addr   = DDC_ADDR,
-                       .flags  = 0,
-                       .len    = 1,
-                       .buf    = &start,
-               }, {
-                       .addr   = DDC_ADDR,
-                       .flags  = I2C_M_RD,
-                       .len    = len,
-                       .buf    = buf,
-               }
-       };
-
-       if (i2c_transfer(adapter, msgs, 2) == 2)
-               return 0;
-
-       return -1;
-}
-
-static u8 *
-drm_do_get_edid(struct drm_connector *connector, struct i2c_adapter *adapter)
-{
-       int i, j = 0, valid_extensions = 0;
-       u8 *block, *new;
-
-       if ((block = kmalloc(EDID_LENGTH, GFP_KERNEL)) == NULL)
-               return NULL;
-
-       /* base block fetch */
-       for (i = 0; i < 4; i++) {
-               if (drm_do_probe_ddc_edid(adapter, block, 0, EDID_LENGTH))
-                       goto out;
-               if (drm_edid_block_valid(block))
-                       break;
-       }
-       if (i == 4)
-               goto carp;
-
-       /* if there's no extensions, we're done */
-       if (block[0x7e] == 0)
-               return block;
-
-       new = krealloc(block, (block[0x7e] + 1) * EDID_LENGTH, GFP_KERNEL);
-       if (!new)
-               goto out;
-       block = new;
-
-       for (j = 1; j <= block[0x7e]; j++) {
-               for (i = 0; i < 4; i++) {
-                       if (drm_do_probe_ddc_edid(adapter,
-                                 block + (valid_extensions + 1) * EDID_LENGTH,
-                                 j, EDID_LENGTH))
-                               goto out;
-                       if (drm_edid_block_valid(block + (valid_extensions + 1) * EDID_LENGTH)) {
-                               valid_extensions++;
-                               break;
-                       }
-               }
-               if (i == 4)
-                       dev_warn(connector->dev->dev,
-                        "%s: Ignoring invalid EDID block %d.\n",
-                        drm_get_connector_name(connector), j);
-       }
-
-       if (valid_extensions != block[0x7e]) {
-               block[EDID_LENGTH-1] += block[0x7e] - valid_extensions;
-               block[0x7e] = valid_extensions;
-               new = krealloc(block, (valid_extensions + 1) * EDID_LENGTH, GFP_KERNEL);
-               if (!new)
-                       goto out;
-               block = new;
-       }
-
-       return block;
-
-carp:
-       dev_warn(connector->dev->dev, "%s: EDID block %d invalid.\n",
-                drm_get_connector_name(connector), j);
-
-out:
-       kfree(block);
-       return NULL;
-}
-
-/**
- * Probe DDC presence.
- *
- * \param adapter : i2c device adaptor
- * \return 1 on success
- */
-static bool
-drm_probe_ddc(struct i2c_adapter *adapter)
-{
-       unsigned char out;
-
-       return (drm_do_probe_ddc_edid(adapter, &out, 0, 1) == 0);
-}
-
-/**
- * drm_get_edid - get EDID data, if available
- * @connector: connector we're probing
- * @adapter: i2c adapter to use for DDC
- *
- * Poke the given i2c channel to grab EDID data if possible.  If found,
- * attach it to the connector.
- *
- * Return edid data or NULL if we couldn't find any.
- */
-struct edid *drm_get_edid(struct drm_connector *connector,
-                         struct i2c_adapter *adapter)
-{
-       struct edid *edid = NULL;
-
-       if (drm_probe_ddc(adapter))
-               edid = (struct edid *)drm_do_get_edid(connector, adapter);
-
-       connector->display_info.raw_edid = (char *)edid;
-
-       return edid;
-
-}
-EXPORT_SYMBOL(drm_get_edid);
-
-/*** EDID parsing ***/
-
-/**
- * edid_vendor - match a string against EDID's obfuscated vendor field
- * @edid: EDID to match
- * @vendor: vendor string
- *
- * Returns true if @vendor is in @edid, false otherwise
- */
-static bool edid_vendor(struct edid *edid, char *vendor)
-{
-       char edid_vendor[3];
-
-       edid_vendor[0] = ((edid->mfg_id[0] & 0x7c) >> 2) + '@';
-       edid_vendor[1] = (((edid->mfg_id[0] & 0x3) << 3) |
-                         ((edid->mfg_id[1] & 0xe0) >> 5)) + '@';
-       edid_vendor[2] = (edid->mfg_id[1] & 0x1f) + '@';
-
-       return !strncmp(edid_vendor, vendor, 3);
-}
-
-/**
- * edid_get_quirks - return quirk flags for a given EDID
- * @edid: EDID to process
- *
- * This tells subsequent routines what fixes they need to apply.
- */
-static u32 edid_get_quirks(struct edid *edid)
-{
-       struct edid_quirk *quirk;
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(edid_quirk_list); i++) {
-               quirk = &edid_quirk_list[i];
-
-               if (edid_vendor(edid, quirk->vendor) &&
-                   (EDID_PRODUCT_ID(edid) == quirk->product_id))
-                       return quirk->quirks;
-       }
-
-       return 0;
-}
-
-#define MODE_SIZE(m) ((m)->hdisplay * (m)->vdisplay)
-#define MODE_REFRESH_DIFF(m,r) (abs((m)->vrefresh - target_refresh))
-
-/**
- * edid_fixup_preferred - set preferred modes based on quirk list
- * @connector: has mode list to fix up
- * @quirks: quirks list
- *
- * Walk the mode list for @connector, clearing the preferred status
- * on existing modes and setting it anew for the right mode ala @quirks.
- */
-static void edid_fixup_preferred(struct drm_connector *connector,
-                                u32 quirks)
-{
-       struct drm_display_mode *t, *cur_mode, *preferred_mode;
-       int target_refresh = 0;
-
-       if (list_empty(&connector->probed_modes))
-               return;
-
-       if (quirks & EDID_QUIRK_PREFER_LARGE_60)
-               target_refresh = 60;
-       if (quirks & EDID_QUIRK_PREFER_LARGE_75)
-               target_refresh = 75;
-
-       preferred_mode = list_first_entry(&connector->probed_modes,
-                                         struct drm_display_mode, head);
-
-       list_for_each_entry_safe(cur_mode, t, &connector->probed_modes, head) {
-               cur_mode->type &= ~DRM_MODE_TYPE_PREFERRED;
-
-               if (cur_mode == preferred_mode)
-                       continue;
-
-               /* Largest mode is preferred */
-               if (MODE_SIZE(cur_mode) > MODE_SIZE(preferred_mode))
-                       preferred_mode = cur_mode;
-
-               /* At a given size, try to get closest to target refresh */
-               if ((MODE_SIZE(cur_mode) == MODE_SIZE(preferred_mode)) &&
-                   MODE_REFRESH_DIFF(cur_mode, target_refresh) <
-                   MODE_REFRESH_DIFF(preferred_mode, target_refresh)) {
-                       preferred_mode = cur_mode;
-               }
-       }
-
-       preferred_mode->type |= DRM_MODE_TYPE_PREFERRED;
-}
-
-struct drm_display_mode *drm_mode_find_dmt(struct drm_device *dev,
-                                          int hsize, int vsize, int fresh)
-{
-       int i;
-       struct drm_display_mode *ptr, *mode;
-
-       mode = NULL;
-       for (i = 0; i < drm_num_dmt_modes; i++) {
-               ptr = &drm_dmt_modes[i];
-               if (hsize == ptr->hdisplay &&
-                       vsize == ptr->vdisplay &&
-                       fresh == drm_mode_vrefresh(ptr)) {
-                       /* get the expected default mode */
-                       mode = drm_mode_duplicate(dev, ptr);
-                       break;
-               }
-       }
-       return mode;
-}
-EXPORT_SYMBOL(drm_mode_find_dmt);
-
-typedef void detailed_cb(struct detailed_timing *timing, void *closure);
-
-static void
-cea_for_each_detailed_block(u8 *ext, detailed_cb *cb, void *closure)
-{
-       int i, n = 0;
-       u8 rev = ext[0x01], d = ext[0x02];
-       u8 *det_base = ext + d;
-
-       switch (rev) {
-       case 0:
-               /* can't happen */
-               return;
-       case 1:
-               /* have to infer how many blocks we have, check pixel clock */
-               for (i = 0; i < 6; i++)
-                       if (det_base[18*i] || det_base[18*i+1])
-                               n++;
-               break;
-       default:
-               /* explicit count */
-               n = min(ext[0x03] & 0x0f, 6);
-               break;
-       }
-
-       for (i = 0; i < n; i++)
-               cb((struct detailed_timing *)(det_base + 18 * i), closure);
-}
-
-static void
-vtb_for_each_detailed_block(u8 *ext, detailed_cb *cb, void *closure)
-{
-       unsigned int i, n = min((int)ext[0x02], 6);
-       u8 *det_base = ext + 5;
-
-       if (ext[0x01] != 1)
-               return; /* unknown version */
-
-       for (i = 0; i < n; i++)
-               cb((struct detailed_timing *)(det_base + 18 * i), closure);
-}
-
-static void
-drm_for_each_detailed_block(u8 *raw_edid, detailed_cb *cb, void *closure)
-{
-       int i;
-       struct edid *edid = (struct edid *)raw_edid;
-
-       if (edid == NULL)
-               return;
-
-       for (i = 0; i < EDID_DETAILED_TIMINGS; i++)
-               cb(&(edid->detailed_timings[i]), closure);
-
-       for (i = 1; i <= raw_edid[0x7e]; i++) {
-               u8 *ext = raw_edid + (i * EDID_LENGTH);
-               switch (*ext) {
-               case CEA_EXT:
-                       cea_for_each_detailed_block(ext, cb, closure);
-                       break;
-               case VTB_EXT:
-                       vtb_for_each_detailed_block(ext, cb, closure);
-                       break;
-               default:
-                       break;
-               }
-       }
-}
-
-static void
-is_rb(struct detailed_timing *t, void *data)
-{
-       u8 *r = (u8 *)t;
-       if (r[3] == EDID_DETAIL_MONITOR_RANGE)
-               if (r[15] & 0x10)
-                       *(bool *)data = true;
-}
-
-/* EDID 1.4 defines this explicitly.  For EDID 1.3, we guess, badly. */
-static bool
-drm_monitor_supports_rb(struct edid *edid)
-{
-       if (edid->revision >= 4) {
-               bool ret;
-               drm_for_each_detailed_block((u8 *)edid, is_rb, &ret);
-               return ret;
-       }
-
-       return ((edid->input & DRM_EDID_INPUT_DIGITAL) != 0);
-}
-
-static void
-find_gtf2(struct detailed_timing *t, void *data)
-{
-       u8 *r = (u8 *)t;
-       if (r[3] == EDID_DETAIL_MONITOR_RANGE && r[10] == 0x02)
-               *(u8 **)data = r;
-}
-
-/* Secondary GTF curve kicks in above some break frequency */
-static int
-drm_gtf2_hbreak(struct edid *edid)
-{
-       u8 *r = NULL;
-       drm_for_each_detailed_block((u8 *)edid, find_gtf2, &r);
-       return r ? (r[12] * 2) : 0;
-}
-
-static int
-drm_gtf2_2c(struct edid *edid)
-{
-       u8 *r = NULL;
-       drm_for_each_detailed_block((u8 *)edid, find_gtf2, &r);
-       return r ? r[13] : 0;
-}
-
-static int
-drm_gtf2_m(struct edid *edid)
-{
-       u8 *r = NULL;
-       drm_for_each_detailed_block((u8 *)edid, find_gtf2, &r);
-       return r ? (r[15] << 8) + r[14] : 0;
-}
-
-static int
-drm_gtf2_k(struct edid *edid)
-{
-       u8 *r = NULL;
-       drm_for_each_detailed_block((u8 *)edid, find_gtf2, &r);
-       return r ? r[16] : 0;
-}
-
-static int
-drm_gtf2_2j(struct edid *edid)
-{
-       u8 *r = NULL;
-       drm_for_each_detailed_block((u8 *)edid, find_gtf2, &r);
-       return r ? r[17] : 0;
-}
-
-/**
- * standard_timing_level - get std. timing level(CVT/GTF/DMT)
- * @edid: EDID block to scan
- */
-static int standard_timing_level(struct edid *edid)
-{
-       if (edid->revision >= 2) {
-               if (edid->revision >= 4 && (edid->features & DRM_EDID_FEATURE_DEFAULT_GTF))
-                       return LEVEL_CVT;
-               if (drm_gtf2_hbreak(edid))
-                       return LEVEL_GTF2;
-               return LEVEL_GTF;
-       }
-       return LEVEL_DMT;
-}
-
-/*
- * 0 is reserved.  The spec says 0x01 fill for unused timings.  Some old
- * monitors fill with ascii space (0x20) instead.
- */
-static int
-bad_std_timing(u8 a, u8 b)
-{
-       return (a == 0x00 && b == 0x00) ||
-              (a == 0x01 && b == 0x01) ||
-              (a == 0x20 && b == 0x20);
-}
-
-/**
- * drm_mode_std - convert standard mode info (width, height, refresh) into mode
- * @t: standard timing params
- * @timing_level: standard timing level
- *
- * Take the standard timing params (in this case width, aspect, and refresh)
- * and convert them into a real mode using CVT/GTF/DMT.
- */
-static struct drm_display_mode *
-drm_mode_std(struct drm_connector *connector, struct edid *edid,
-            struct std_timing *t, int revision)
-{
-       struct drm_device *dev = connector->dev;
-       struct drm_display_mode *m, *mode = NULL;
-       int hsize, vsize;
-       int vrefresh_rate;
-       unsigned aspect_ratio = (t->vfreq_aspect & EDID_TIMING_ASPECT_MASK)
-               >> EDID_TIMING_ASPECT_SHIFT;
-       unsigned vfreq = (t->vfreq_aspect & EDID_TIMING_VFREQ_MASK)
-               >> EDID_TIMING_VFREQ_SHIFT;
-       int timing_level = standard_timing_level(edid);
-
-       if (bad_std_timing(t->hsize, t->vfreq_aspect))
-               return NULL;
-
-       /* According to the EDID spec, the hdisplay = hsize * 8 + 248 */
-       hsize = t->hsize * 8 + 248;
-       /* vrefresh_rate = vfreq + 60 */
-       vrefresh_rate = vfreq + 60;
-       /* the vdisplay is calculated based on the aspect ratio */
-       if (aspect_ratio == 0) {
-               if (revision < 3)
-                       vsize = hsize;
-               else
-                       vsize = (hsize * 10) / 16;
-       } else if (aspect_ratio == 1)
-               vsize = (hsize * 3) / 4;
-       else if (aspect_ratio == 2)
-               vsize = (hsize * 4) / 5;
-       else
-               vsize = (hsize * 9) / 16;
-
-       /* HDTV hack, part 1 */
-       if (vrefresh_rate == 60 &&
-           ((hsize == 1360 && vsize == 765) ||
-            (hsize == 1368 && vsize == 769))) {
-               hsize = 1366;
-               vsize = 768;
-       }
-
-       /*
-        * If this connector already has a mode for this size and refresh
-        * rate (because it came from detailed or CVT info), use that
-        * instead.  This way we don't have to guess at interlace or
-        * reduced blanking.
-        */
-       list_for_each_entry(m, &connector->probed_modes, head)
-               if (m->hdisplay == hsize && m->vdisplay == vsize &&
-                   drm_mode_vrefresh(m) == vrefresh_rate)
-                       return NULL;
-
-       /* HDTV hack, part 2 */
-       if (hsize == 1366 && vsize == 768 && vrefresh_rate == 60) {
-               mode = drm_cvt_mode(dev, 1366, 768, vrefresh_rate, 0, 0,
-                                   false);
-               mode->hdisplay = 1366;
-               mode->hsync_start = mode->hsync_start - 1;
-               mode->hsync_end = mode->hsync_end - 1;
-               return mode;
-       }
-
-       /* check whether it can be found in default mode table */
-       mode = drm_mode_find_dmt(dev, hsize, vsize, vrefresh_rate);
-       if (mode)
-               return mode;
-
-       switch (timing_level) {
-       case LEVEL_DMT:
-               break;
-       case LEVEL_GTF:
-               mode = drm_gtf_mode(dev, hsize, vsize, vrefresh_rate, 0, 0);
-               break;
-       case LEVEL_GTF2:
-               /*
-                * This is potentially wrong if there's ever a monitor with
-                * more than one ranges section, each claiming a different
-                * secondary GTF curve.  Please don't do that.
-                */
-               mode = drm_gtf_mode(dev, hsize, vsize, vrefresh_rate, 0, 0);
-               if (drm_mode_hsync(mode) > drm_gtf2_hbreak(edid)) {
-                       kfree(mode);
-                       mode = drm_gtf_mode_complex(dev, hsize, vsize,
-                                                   vrefresh_rate, 0, 0,
-                                                   drm_gtf2_m(edid),
-                                                   drm_gtf2_2c(edid),
-                                                   drm_gtf2_k(edid),
-                                                   drm_gtf2_2j(edid));
-               }
-               break;
-       case LEVEL_CVT:
-               mode = drm_cvt_mode(dev, hsize, vsize, vrefresh_rate, 0, 0,
-                                   false);
-               break;
-       }
-       return mode;
-}
-
-/*
- * EDID is delightfully ambiguous about how interlaced modes are to be
- * encoded.  Our internal representation is of frame height, but some
- * HDTV detailed timings are encoded as field height.
- *
- * The format list here is from CEA, in frame size.  Technically we
- * should be checking refresh rate too.  Whatever.
- */
-static void
-drm_mode_do_interlace_quirk(struct drm_display_mode *mode,
-                           struct detailed_pixel_timing *pt)
-{
-       int i;
-       static const struct {
-               int w, h;
-       } cea_interlaced[] = {
-               { 1920, 1080 },
-               {  720,  480 },
-               { 1440,  480 },
-               { 2880,  480 },
-               {  720,  576 },
-               { 1440,  576 },
-               { 2880,  576 },
-       };
-
-       if (!(pt->misc & DRM_EDID_PT_INTERLACED))
-               return;
-
-       for (i = 0; i < ARRAY_SIZE(cea_interlaced); i++) {
-               if ((mode->hdisplay == cea_interlaced[i].w) &&
-                   (mode->vdisplay == cea_interlaced[i].h / 2)) {
-                       mode->vdisplay *= 2;
-                       mode->vsync_start *= 2;
-                       mode->vsync_end *= 2;
-                       mode->vtotal *= 2;
-                       mode->vtotal |= 1;
-               }
-       }
-
-       mode->flags |= DRM_MODE_FLAG_INTERLACE;
-}
-
-/**
- * drm_mode_detailed - create a new mode from an EDID detailed timing section
- * @dev: DRM device (needed to create new mode)
- * @edid: EDID block
- * @timing: EDID detailed timing info
- * @quirks: quirks to apply
- *
- * An EDID detailed timing block contains enough info for us to create and
- * return a new struct drm_display_mode.
- */
-static struct drm_display_mode *drm_mode_detailed(struct drm_device *dev,
-                                                 struct edid *edid,
-                                                 struct detailed_timing *timing,
-                                                 u32 quirks)
-{
-       struct drm_display_mode *mode;
-       struct detailed_pixel_timing *pt = &timing->data.pixel_data;
-       unsigned hactive = (pt->hactive_hblank_hi & 0xf0) << 4 | pt->hactive_lo;
-       unsigned vactive = (pt->vactive_vblank_hi & 0xf0) << 4 | pt->vactive_lo;
-       unsigned hblank = (pt->hactive_hblank_hi & 0xf) << 8 | pt->hblank_lo;
-       unsigned vblank = (pt->vactive_vblank_hi & 0xf) << 8 | pt->vblank_lo;
-       unsigned hsync_offset = (pt->hsync_vsync_offset_pulse_width_hi & 0xc0) << 2 | pt->hsync_offset_lo;
-       unsigned hsync_pulse_width = (pt->hsync_vsync_offset_pulse_width_hi & 0x30) << 4 | pt->hsync_pulse_width_lo;
-       unsigned vsync_offset = (pt->hsync_vsync_offset_pulse_width_hi & 0xc) >> 2 | pt->vsync_offset_pulse_width_lo >> 4;
-       unsigned vsync_pulse_width = (pt->hsync_vsync_offset_pulse_width_hi & 0x3) << 4 | (pt->vsync_offset_pulse_width_lo & 0xf);
-
-       /* ignore tiny modes */
-       if (hactive < 64 || vactive < 64)
-               return NULL;
-
-       if (pt->misc & DRM_EDID_PT_STEREO) {
-               printk(KERN_WARNING "stereo mode not supported\n");
-               return NULL;
-       }
-       if (!(pt->misc & DRM_EDID_PT_SEPARATE_SYNC)) {
-               printk(KERN_WARNING "composite sync not supported\n");
-       }
-
-       /* it is incorrect if hsync/vsync width is zero */
-       if (!hsync_pulse_width || !vsync_pulse_width) {
-               DRM_DEBUG_KMS("Incorrect Detailed timing. "
-                               "Wrong Hsync/Vsync pulse width\n");
-               return NULL;
-       }
-       mode = drm_mode_create(dev);
-       if (!mode)
-               return NULL;
-
-       mode->type = DRM_MODE_TYPE_DRIVER;
-
-       if (quirks & EDID_QUIRK_135_CLOCK_TOO_HIGH)
-               timing->pixel_clock = cpu_to_le16(1088);
-
-       mode->clock = le16_to_cpu(timing->pixel_clock) * 10;
-
-       mode->hdisplay = hactive;
-       mode->hsync_start = mode->hdisplay + hsync_offset;
-       mode->hsync_end = mode->hsync_start + hsync_pulse_width;
-       mode->htotal = mode->hdisplay + hblank;
-
-       mode->vdisplay = vactive;
-       mode->vsync_start = mode->vdisplay + vsync_offset;
-       mode->vsync_end = mode->vsync_start + vsync_pulse_width;
-       mode->vtotal = mode->vdisplay + vblank;
-
-       /* Some EDIDs have bogus h/vtotal values */
-       if (mode->hsync_end > mode->htotal)
-               mode->htotal = mode->hsync_end + 1;
-       if (mode->vsync_end > mode->vtotal)
-               mode->vtotal = mode->vsync_end + 1;
-
-       drm_mode_do_interlace_quirk(mode, pt);
-
-       drm_mode_set_name(mode);
-
-       if (quirks & EDID_QUIRK_DETAILED_SYNC_PP) {
-               pt->misc |= DRM_EDID_PT_HSYNC_POSITIVE | DRM_EDID_PT_VSYNC_POSITIVE;
-       }
-
-       mode->flags |= (pt->misc & DRM_EDID_PT_HSYNC_POSITIVE) ?
-               DRM_MODE_FLAG_PHSYNC : DRM_MODE_FLAG_NHSYNC;
-       mode->flags |= (pt->misc & DRM_EDID_PT_VSYNC_POSITIVE) ?
-               DRM_MODE_FLAG_PVSYNC : DRM_MODE_FLAG_NVSYNC;
-
-       mode->width_mm = pt->width_mm_lo | (pt->width_height_mm_hi & 0xf0) << 4;
-       mode->height_mm = pt->height_mm_lo | (pt->width_height_mm_hi & 0xf) << 8;
-
-       if (quirks & EDID_QUIRK_DETAILED_IN_CM) {
-               mode->width_mm *= 10;
-               mode->height_mm *= 10;
-       }
-
-       if (quirks & EDID_QUIRK_DETAILED_USE_MAXIMUM_SIZE) {
-               mode->width_mm = edid->width_cm * 10;
-               mode->height_mm = edid->height_cm * 10;
-       }
-
-       return mode;
-}
-
-static bool
-mode_is_rb(struct drm_display_mode *mode)
-{
-       return (mode->htotal - mode->hdisplay == 160) &&
-              (mode->hsync_end - mode->hdisplay == 80) &&
-              (mode->hsync_end - mode->hsync_start == 32) &&
-              (mode->vsync_start - mode->vdisplay == 3);
-}
-
-static bool
-mode_in_hsync_range(struct drm_display_mode *mode, struct edid *edid, u8 *t)
-{
-       int hsync, hmin, hmax;
-
-       hmin = t[7];
-       if (edid->revision >= 4)
-           hmin += ((t[4] & 0x04) ? 255 : 0);
-       hmax = t[8];
-       if (edid->revision >= 4)
-           hmax += ((t[4] & 0x08) ? 255 : 0);
-       hsync = drm_mode_hsync(mode);
-
-       return (hsync <= hmax && hsync >= hmin);
-}
-
-static bool
-mode_in_vsync_range(struct drm_display_mode *mode, struct edid *edid, u8 *t)
-{
-       int vsync, vmin, vmax;
-
-       vmin = t[5];
-       if (edid->revision >= 4)
-           vmin += ((t[4] & 0x01) ? 255 : 0);
-       vmax = t[6];
-       if (edid->revision >= 4)
-           vmax += ((t[4] & 0x02) ? 255 : 0);
-       vsync = drm_mode_vrefresh(mode);
-
-       return (vsync <= vmax && vsync >= vmin);
-}
-
-static u32
-range_pixel_clock(struct edid *edid, u8 *t)
-{
-       /* unspecified */
-       if (t[9] == 0 || t[9] == 255)
-               return 0;
-
-       /* 1.4 with CVT support gives us real precision, yay */
-       if (edid->revision >= 4 && t[10] == 0x04)
-               return (t[9] * 10000) - ((t[12] >> 2) * 250);
-
-       /* 1.3 is pathetic, so fuzz up a bit */
-       return t[9] * 10000 + 5001;
-}
-
-static bool
-mode_in_range(struct drm_display_mode *mode, struct edid *edid,
-             struct detailed_timing *timing)
-{
-       u32 max_clock;
-       u8 *t = (u8 *)timing;
-
-       if (!mode_in_hsync_range(mode, edid, t))
-               return false;
-
-       if (!mode_in_vsync_range(mode, edid, t))
-               return false;
-
-       if ((max_clock = range_pixel_clock(edid, t)))
-               if (mode->clock > max_clock)
-                       return false;
-
-       /* 1.4 max horizontal check */
-       if (edid->revision >= 4 && t[10] == 0x04)
-               if (t[13] && mode->hdisplay > 8 * (t[13] + (256 * (t[12]&0x3))))
-                       return false;
-
-       if (mode_is_rb(mode) && !drm_monitor_supports_rb(edid))
-               return false;
-
-       return true;
-}
-
-/*
- * XXX If drm_dmt_modes ever regrows the CVT-R modes (and it will) this will
- * need to account for them.
- */
-static int
-drm_gtf_modes_for_range(struct drm_connector *connector, struct edid *edid,
-                       struct detailed_timing *timing)
-{
-       int i, modes = 0;
-       struct drm_display_mode *newmode;
-       struct drm_device *dev = connector->dev;
-
-       for (i = 0; i < drm_num_dmt_modes; i++) {
-               if (mode_in_range(drm_dmt_modes + i, edid, timing)) {
-                       newmode = drm_mode_duplicate(dev, &drm_dmt_modes[i]);
-                       if (newmode) {
-                               drm_mode_probed_add(connector, newmode);
-                               modes++;
-                       }
-               }
-       }
-
-       return modes;
-}
-
-static void
-do_inferred_modes(struct detailed_timing *timing, void *c)
-{
-       struct detailed_mode_closure *closure = c;
-       struct detailed_non_pixel *data = &timing->data.other_data;
-       int gtf = (closure->edid->features & DRM_EDID_FEATURE_DEFAULT_GTF);
-
-       if (gtf && data->type == EDID_DETAIL_MONITOR_RANGE)
-               closure->modes += drm_gtf_modes_for_range(closure->connector,
-                                                         closure->edid,
-                                                         timing);
-}
-
-static int
-add_inferred_modes(struct drm_connector *connector, struct edid *edid)
-{
-       struct detailed_mode_closure closure = {
-               connector, edid, 0, 0, 0
-       };
-
-       if (version_greater(edid, 1, 0))
-               drm_for_each_detailed_block((u8 *)edid, do_inferred_modes,
-                                           &closure);
-
-       return closure.modes;
-}
-
-static int
-drm_est3_modes(struct drm_connector *connector, struct detailed_timing *timing)
-{
-       int i, j, m, modes = 0;
-       struct drm_display_mode *mode;
-       u8 *est = ((u8 *)timing) + 5;
-
-       for (i = 0; i < 6; i++) {
-               for (j = 7; j > 0; j--) {
-                       m = (i * 8) + (7 - j);
-                       if (m >= ARRAY_SIZE(est3_modes))
-                               break;
-                       if (est[i] & (1 << j)) {
-                               mode = drm_mode_find_dmt(connector->dev,
-                                                        est3_modes[m].w,
-                                                        est3_modes[m].h,
-                                                        est3_modes[m].r
-                                                        /*, est3_modes[m].rb */);
-                               if (mode) {
-                                       drm_mode_probed_add(connector, mode);
-                                       modes++;
-                               }
-                       }
-               }
-       }
-
-       return modes;
-}
-
-static void
-do_established_modes(struct detailed_timing *timing, void *c)
-{
-       struct detailed_mode_closure *closure = c;
-       struct detailed_non_pixel *data = &timing->data.other_data;
-
-       if (data->type == EDID_DETAIL_EST_TIMINGS)
-               closure->modes += drm_est3_modes(closure->connector, timing);
-}
-
-/**
- * add_established_modes - get est. modes from EDID and add them
- * @edid: EDID block to scan
- *
- * Each EDID block contains a bitmap of the supported "established modes" list
- * (defined above).  Tease them out and add them to the global modes list.
- */
-static int
-add_established_modes(struct drm_connector *connector, struct edid *edid)
-{
-       struct drm_device *dev = connector->dev;
-       unsigned long est_bits = edid->established_timings.t1 |
-               (edid->established_timings.t2 << 8) |
-               ((edid->established_timings.mfg_rsvd & 0x80) << 9);
-       int i, modes = 0;
-       struct detailed_mode_closure closure = {
-               connector, edid, 0, 0, 0
-       };
-
-       for (i = 0; i <= EDID_EST_TIMINGS; i++) {
-               if (est_bits & (1<<i)) {
-                       struct drm_display_mode *newmode;
-                       newmode = drm_mode_duplicate(dev, &edid_est_modes[i]);
-                       if (newmode) {
-                               drm_mode_probed_add(connector, newmode);
-                               modes++;
-                       }
-               }
-       }
-
-       if (version_greater(edid, 1, 0))
-                   drm_for_each_detailed_block((u8 *)edid,
-                                               do_established_modes, &closure);
-
-       return modes + closure.modes;
-}
-
-static void
-do_standard_modes(struct detailed_timing *timing, void *c)
-{
-       struct detailed_mode_closure *closure = c;
-       struct detailed_non_pixel *data = &timing->data.other_data;
-       struct drm_connector *connector = closure->connector;
-       struct edid *edid = closure->edid;
-
-       if (data->type == EDID_DETAIL_STD_MODES) {
-               int i;
-               for (i = 0; i < 6; i++) {
-                       struct std_timing *std;
-                       struct drm_display_mode *newmode;
-
-                       std = &data->data.timings[i];
-                       newmode = drm_mode_std(connector, edid, std,
-                                              edid->revision);
-                       if (newmode) {
-                               drm_mode_probed_add(connector, newmode);
-                               closure->modes++;
-                       }
-               }
-       }
-}
-
-/**
- * add_standard_modes - get std. modes from EDID and add them
- * @edid: EDID block to scan
- *
- * Standard modes can be calculated using the appropriate standard (DMT,
- * GTF or CVT. Grab them from @edid and add them to the list.
- */
-static int
-add_standard_modes(struct drm_connector *connector, struct edid *edid)
-{
-       int i, modes = 0;
-       struct detailed_mode_closure closure = {
-               connector, edid, 0, 0, 0
-       };
-
-       for (i = 0; i < EDID_STD_TIMINGS; i++) {
-               struct drm_display_mode *newmode;
-
-               newmode = drm_mode_std(connector, edid,
-                                      &edid->standard_timings[i],
-                                      edid->revision);
-               if (newmode) {
-                       drm_mode_probed_add(connector, newmode);
-                       modes++;
-               }
-       }
-
-       if (version_greater(edid, 1, 0))
-               drm_for_each_detailed_block((u8 *)edid, do_standard_modes,
-                                           &closure);
-
-       /* XXX should also look for standard codes in VTB blocks */
-
-       return modes + closure.modes;
-}
-
-static int drm_cvt_modes(struct drm_connector *connector,
-                        struct detailed_timing *timing)
-{
-       int i, j, modes = 0;
-       struct drm_display_mode *newmode;
-       struct drm_device *dev = connector->dev;
-       struct cvt_timing *cvt;
-       const int rates[] = { 60, 85, 75, 60, 50 };
-       const u8 empty[3] = { 0, 0, 0 };
-
-       for (i = 0; i < 4; i++) {
-               int uninitialized_var(width), height;
-               cvt = &(timing->data.other_data.data.cvt[i]);
-
-               if (!memcmp(cvt->code, empty, 3))
-                       continue;
-
-               height = (cvt->code[0] + ((cvt->code[1] & 0xf0) << 4) + 1) * 2;
-               switch (cvt->code[1] & 0x0c) {
-               case 0x00:
-                       width = height * 4 / 3;
-                       break;
-               case 0x04:
-                       width = height * 16 / 9;
-                       break;
-               case 0x08:
-                       width = height * 16 / 10;
-                       break;
-               case 0x0c:
-                       width = height * 15 / 9;
-                       break;
-               }
-
-               for (j = 1; j < 5; j++) {
-                       if (cvt->code[2] & (1 << j)) {
-                               newmode = drm_cvt_mode(dev, width, height,
-                                                      rates[j], j == 0,
-                                                      false, false);
-                               if (newmode) {
-                                       drm_mode_probed_add(connector, newmode);
-                                       modes++;
-                               }
-                       }
-               }
-       }
-
-       return modes;
-}
-
-static void
-do_cvt_mode(struct detailed_timing *timing, void *c)
-{
-       struct detailed_mode_closure *closure = c;
-       struct detailed_non_pixel *data = &timing->data.other_data;
-
-       if (data->type == EDID_DETAIL_CVT_3BYTE)
-               closure->modes += drm_cvt_modes(closure->connector, timing);
-}
-
-static int
-add_cvt_modes(struct drm_connector *connector, struct edid *edid)
-{      
-       struct detailed_mode_closure closure = {
-               connector, edid, 0, 0, 0
-       };
-
-       if (version_greater(edid, 1, 2))
-               drm_for_each_detailed_block((u8 *)edid, do_cvt_mode, &closure);
-
-       /* XXX should also look for CVT codes in VTB blocks */
-
-       return closure.modes;
-}
-
-static void
-do_detailed_mode(struct detailed_timing *timing, void *c)
-{
-       struct detailed_mode_closure *closure = c;
-       struct drm_display_mode *newmode;
-
-       if (timing->pixel_clock) {
-               newmode = drm_mode_detailed(closure->connector->dev,
-                                           closure->edid, timing,
-                                           closure->quirks);
-               if (!newmode)
-                       return;
-
-               if (closure->preferred)
-                       newmode->type |= DRM_MODE_TYPE_PREFERRED;
-
-               drm_mode_probed_add(closure->connector, newmode);
-               closure->modes++;
-               closure->preferred = 0;
-       }
-}
-
-/*
- * add_detailed_modes - Add modes from detailed timings
- * @connector: attached connector
- * @edid: EDID block to scan
- * @quirks: quirks to apply
- */
-static int
-add_detailed_modes(struct drm_connector *connector, struct edid *edid,
-                  u32 quirks)
-{
-       struct detailed_mode_closure closure = {
-               connector,
-               edid,
-               1,
-               quirks,
-               0
-       };
-
-       if (closure.preferred && !version_greater(edid, 1, 3))
-               closure.preferred =
-                   (edid->features & DRM_EDID_FEATURE_PREFERRED_TIMING);
-
-       drm_for_each_detailed_block((u8 *)edid, do_detailed_mode, &closure);
-
-       return closure.modes;
-}
-
-#define HDMI_IDENTIFIER 0x000C03
-#define AUDIO_BLOCK    0x01
-#define VENDOR_BLOCK    0x03
-#define EDID_BASIC_AUDIO       (1 << 6)
-
-/**
- * Search EDID for CEA extension block.
- */
-static u8 *drm_find_cea_extension(struct edid *edid)
-{
-       u8 *edid_ext = NULL;
-       int i;
-
-       /* No EDID or EDID extensions */
-       if (edid == NULL || edid->extensions == 0)
-               return NULL;
-
-       /* Find CEA extension */
-       for (i = 0; i < edid->extensions; i++) {
-               edid_ext = (u8 *)edid + EDID_LENGTH * (i + 1);
-               if (edid_ext[0] == CEA_EXT)
-                       break;
-       }
-
-       if (i == edid->extensions)
-               return NULL;
-
-       return edid_ext;
-}
-
-/**
- * drm_detect_hdmi_monitor - detect whether monitor is hdmi.
- * @edid: monitor EDID information
- *
- * Parse the CEA extension according to CEA-861-B.
- * Return true if HDMI, false if not or unknown.
- */
-bool drm_detect_hdmi_monitor(struct edid *edid)
-{
-       u8 *edid_ext;
-       int i, hdmi_id;
-       int start_offset, end_offset;
-       bool is_hdmi = false;
-
-       edid_ext = drm_find_cea_extension(edid);
-       if (!edid_ext)
-               goto end;
-
-       /* Data block offset in CEA extension block */
-       start_offset = 4;
-       end_offset = edid_ext[2];
-
-       /*
-        * Because HDMI identifier is in Vendor Specific Block,
-        * search it from all data blocks of CEA extension.
-        */
-       for (i = start_offset; i < end_offset;
-               /* Increased by data block len */
-               i += ((edid_ext[i] & 0x1f) + 1)) {
-               /* Find vendor specific block */
-               if ((edid_ext[i] >> 5) == VENDOR_BLOCK) {
-                       hdmi_id = edid_ext[i + 1] | (edid_ext[i + 2] << 8) |
-                                 edid_ext[i + 3] << 16;
-                       /* Find HDMI identifier */
-                       if (hdmi_id == HDMI_IDENTIFIER)
-                               is_hdmi = true;
-                       break;
-               }
-       }
-
-end:
-       return is_hdmi;
-}
-EXPORT_SYMBOL(drm_detect_hdmi_monitor);
-
-/**
- * drm_detect_monitor_audio - check monitor audio capability
- *
- * Monitor should have CEA extension block.
- * If monitor has 'basic audio', but no CEA audio blocks, it's 'basic
- * audio' only. If there is any audio extension block and supported
- * audio format, assume at least 'basic audio' support, even if 'basic
- * audio' is not defined in EDID.
- *
- */
-bool drm_detect_monitor_audio(struct edid *edid)
-{
-       u8 *edid_ext;
-       int i, j;
-       bool has_audio = false;
-       int start_offset, end_offset;
-
-       edid_ext = drm_find_cea_extension(edid);
-       if (!edid_ext)
-               goto end;
-
-       has_audio = ((edid_ext[3] & EDID_BASIC_AUDIO) != 0);
-
-       if (has_audio) {
-               DRM_DEBUG_KMS("Monitor has basic audio support\n");
-               goto end;
-       }
-
-       /* Data block offset in CEA extension block */
-       start_offset = 4;
-       end_offset = edid_ext[2];
-
-       for (i = start_offset; i < end_offset;
-                       i += ((edid_ext[i] & 0x1f) + 1)) {
-               if ((edid_ext[i] >> 5) == AUDIO_BLOCK) {
-                       has_audio = true;
-                       for (j = 1; j < (edid_ext[i] & 0x1f); j += 3)
-                               DRM_DEBUG_KMS("CEA audio format %d\n",
-                                             (edid_ext[i + j] >> 3) & 0xf);
-                       goto end;
-               }
-       }
-end:
-       return has_audio;
-}
-EXPORT_SYMBOL(drm_detect_monitor_audio);
-
-/**
- * drm_add_edid_modes - add modes from EDID data, if available
- * @connector: connector we're probing
- * @edid: edid data
- *
- * Add the specified modes to the connector's mode list.
- *
- * Return number of modes added or 0 if we couldn't find any.
- */
-int drm_add_edid_modes(struct drm_connector *connector, struct edid *edid)
-{
-       int num_modes = 0;
-       u32 quirks;
-
-       if (edid == NULL) {
-               return 0;
-       }
-       if (!drm_edid_is_valid(edid)) {
-               dev_warn(connector->dev->dev, "%s: EDID invalid.\n",
-                        drm_get_connector_name(connector));
-               return 0;
-       }
-
-       quirks = edid_get_quirks(edid);
-
-       /*
-        * EDID spec says modes should be preferred in this order:
-        * - preferred detailed mode
-        * - other detailed modes from base block
-        * - detailed modes from extension blocks
-        * - CVT 3-byte code modes
-        * - standard timing codes
-        * - established timing codes
-        * - modes inferred from GTF or CVT range information
-        *
-        * We get this pretty much right.
-        *
-        * XXX order for additional mode types in extension blocks?
-        */
-       num_modes += add_detailed_modes(connector, edid, quirks);
-       num_modes += add_cvt_modes(connector, edid);
-       num_modes += add_standard_modes(connector, edid);
-       num_modes += add_established_modes(connector, edid);
-       num_modes += add_inferred_modes(connector, edid);
-
-       if (quirks & (EDID_QUIRK_PREFER_LARGE_60 | EDID_QUIRK_PREFER_LARGE_75))
-               edid_fixup_preferred(connector, quirks);
-
-       connector->display_info.width_mm = edid->width_cm * 10;
-       connector->display_info.height_mm = edid->height_cm * 10;
-
-       return num_modes;
-}
-EXPORT_SYMBOL(drm_add_edid_modes);
-
-/**
- * drm_add_modes_noedid - add modes for the connectors without EDID
- * @connector: connector we're probing
- * @hdisplay: the horizontal display limit
- * @vdisplay: the vertical display limit
- *
- * Add the specified modes to the connector's mode list. Only when the
- * hdisplay/vdisplay is not beyond the given limit, it will be added.
- *
- * Return number of modes added or 0 if we couldn't find any.
- */
-int drm_add_modes_noedid(struct drm_connector *connector,
-                       int hdisplay, int vdisplay)
-{
-       int i, count, num_modes = 0;
-       struct drm_display_mode *mode, *ptr;
-       struct drm_device *dev = connector->dev;
-
-       count = sizeof(drm_dmt_modes) / sizeof(struct drm_display_mode);
-       if (hdisplay < 0)
-               hdisplay = 0;
-       if (vdisplay < 0)
-               vdisplay = 0;
-
-       for (i = 0; i < count; i++) {
-               ptr = &drm_dmt_modes[i];
-               if (hdisplay && vdisplay) {
-                       /*
-                        * Only when two are valid, they will be used to check
-                        * whether the mode should be added to the mode list of
-                        * the connector.
-                        */
-                       if (ptr->hdisplay > hdisplay ||
-                                       ptr->vdisplay > vdisplay)
-                               continue;
-               }
-               if (drm_mode_vrefresh(ptr) > 61)
-                       continue;
-               mode = drm_mode_duplicate(dev, ptr);
-               if (mode) {
-                       drm_mode_probed_add(connector, mode);
-                       num_modes++;
-               }
-       }
-       return num_modes;
-}
-EXPORT_SYMBOL(drm_add_modes_noedid);
diff --git a/services4/3rdparty/linux_drm/drm_encoder_slave.c b/services4/3rdparty/linux_drm/drm_encoder_slave.c
deleted file mode 100644 (file)
index d62c064..0000000
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * Copyright (C) 2009 Francisco Jerez.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice (including the
- * next paragraph) shall be included in all copies or substantial
- * portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
- * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-
-#include "drm_encoder_slave.h"
-
-/**
- * drm_i2c_encoder_init - Initialize an I2C slave encoder
- * @dev:       DRM device.
- * @encoder:    Encoder to be attached to the I2C device. You aren't
- *             required to have called drm_encoder_init() before.
- * @adap:      I2C adapter that will be used to communicate with
- *             the device.
- * @info:      Information that will be used to create the I2C device.
- *             Required fields are @addr and @type.
- *
- * Create an I2C device on the specified bus (the module containing its
- * driver is transparently loaded) and attach it to the specified
- * &drm_encoder_slave. The @slave_funcs field will be initialized with
- * the hooks provided by the slave driver.
- *
- * If @info->platform_data is non-NULL it will be used as the initial
- * slave config.
- *
- * Returns 0 on success or a negative errno on failure, in particular,
- * -ENODEV is returned when no matching driver is found.
- */
-int drm_i2c_encoder_init(struct drm_device *dev,
-                        struct drm_encoder_slave *encoder,
-                        struct i2c_adapter *adap,
-                        const struct i2c_board_info *info)
-{
-       char modalias[sizeof(I2C_MODULE_PREFIX)
-                     + I2C_NAME_SIZE];
-       struct module *module = NULL;
-       struct i2c_client *client;
-       struct drm_i2c_encoder_driver *encoder_drv;
-       int err = 0;
-
-       snprintf(modalias, sizeof(modalias),
-                "%s%s", I2C_MODULE_PREFIX, info->type);
-       request_module(modalias);
-
-       client = i2c_new_device(adap, info);
-       if (!client) {
-               err = -ENOMEM;
-               goto fail;
-       }
-
-       if (!client->driver) {
-               err = -ENODEV;
-               goto fail_unregister;
-       }
-
-       module = client->driver->driver.owner;
-       if (!try_module_get(module)) {
-               err = -ENODEV;
-               goto fail_unregister;
-       }
-
-       encoder->bus_priv = client;
-
-       encoder_drv = to_drm_i2c_encoder_driver(client->driver);
-
-       err = encoder_drv->encoder_init(client, dev, encoder);
-       if (err)
-               goto fail_unregister;
-
-       if (info->platform_data)
-               encoder->slave_funcs->set_config(&encoder->base,
-                                                info->platform_data);
-
-       return 0;
-
-fail_unregister:
-       i2c_unregister_device(client);
-       module_put(module);
-fail:
-       return err;
-}
-EXPORT_SYMBOL(drm_i2c_encoder_init);
-
-/**
- * drm_i2c_encoder_destroy - Unregister the I2C device backing an encoder
- * @drm_encoder:       Encoder to be unregistered.
- *
- * This should be called from the @destroy method of an I2C slave
- * encoder driver once I2C access is no longer needed.
- */
-void drm_i2c_encoder_destroy(struct drm_encoder *drm_encoder)
-{
-       struct drm_encoder_slave *encoder = to_encoder_slave(drm_encoder);
-       struct i2c_client *client = drm_i2c_encoder_get_client(drm_encoder);
-       struct module *module = client->driver->driver.owner;
-
-       i2c_unregister_device(client);
-       encoder->bus_priv = NULL;
-
-       module_put(module);
-}
-EXPORT_SYMBOL(drm_i2c_encoder_destroy);
diff --git a/services4/3rdparty/linux_drm/drm_fb_helper.c b/services4/3rdparty/linux_drm/drm_fb_helper.c
deleted file mode 100644 (file)
index d2849e4..0000000
+++ /dev/null
@@ -1,1532 +0,0 @@
-/*
- * Copyright (c) 2006-2009 Red Hat Inc.
- * Copyright (c) 2006-2008 Intel Corporation
- * Copyright (c) 2007 Dave Airlie <airlied@linux.ie>
- *
- * DRM framebuffer helper functions
- *
- * Permission to use, copy, modify, distribute, and sell this software and its
- * documentation for any purpose is hereby granted without fee, provided that
- * the above copyright notice appear in all copies and that both that copyright
- * notice and this permission notice appear in supporting documentation, and
- * that the name of the copyright holders not be used in advertising or
- * publicity pertaining to distribution of the software without specific,
- * written prior permission.  The copyright holders make no representations
- * about the suitability of this software for any purpose.  It is provided "as
- * is" without express or implied warranty.
- *
- * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
- * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
- * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
- * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
- * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
- * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
- * OF THIS SOFTWARE.
- *
- * Authors:
- *      Dave Airlie <airlied@linux.ie>
- *      Jesse Barnes <jesse.barnes@intel.com>
- */
-#include <linux/kernel.h>
-#include <linux/sysrq.h>
-#include <linux/slab.h>
-#include <linux/fb.h>
-#include "drmP.h"
-#include "drm_crtc.h"
-#include "drm_fb_helper.h"
-#include "drm_crtc_helper.h"
-
-MODULE_AUTHOR("David Airlie, Jesse Barnes");
-MODULE_DESCRIPTION("DRM KMS helper");
-MODULE_LICENSE("GPL and additional rights");
-
-static LIST_HEAD(kernel_fb_helper_list);
-
-/* simple single crtc case helper function */
-int drm_fb_helper_single_add_all_connectors(struct drm_fb_helper *fb_helper)
-{
-       struct drm_device *dev = fb_helper->dev;
-       struct drm_connector *connector;
-       int i;
-
-       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
-               struct drm_fb_helper_connector *fb_helper_connector;
-
-               fb_helper_connector = kzalloc(sizeof(struct drm_fb_helper_connector), GFP_KERNEL);
-               if (!fb_helper_connector)
-                       goto fail;
-
-               fb_helper_connector->connector = connector;
-               fb_helper->connector_info[fb_helper->connector_count++] = fb_helper_connector;
-       }
-       return 0;
-fail:
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               kfree(fb_helper->connector_info[i]);
-               fb_helper->connector_info[i] = NULL;
-       }
-       fb_helper->connector_count = 0;
-       return -ENOMEM;
-}
-EXPORT_SYMBOL(drm_fb_helper_single_add_all_connectors);
-
-/**
- * drm_fb_helper_connector_parse_command_line - parse command line for connector
- * @connector - connector to parse line for
- * @mode_option - per connector mode option
- *
- * This parses the connector specific then generic command lines for
- * modes and options to configure the connector.
- *
- * This uses the same parameters as the fb modedb.c, except for extra
- *     <xres>x<yres>[M][R][-<bpp>][@<refresh>][i][m][eDd]
- *
- * enable/enable Digital/disable bit at the end
- */
-static bool drm_fb_helper_connector_parse_command_line(struct drm_fb_helper_connector *fb_helper_conn,
-                                                      const char *mode_option)
-{
-       const char *name;
-       unsigned int namelen;
-       int res_specified = 0, bpp_specified = 0, refresh_specified = 0;
-       unsigned int xres = 0, yres = 0, bpp = 32, refresh = 0;
-       int yres_specified = 0, cvt = 0, rb = 0, interlace = 0, margins = 0;
-       int i;
-       enum drm_connector_force force = DRM_FORCE_UNSPECIFIED;
-       struct drm_fb_helper_cmdline_mode *cmdline_mode;
-       struct drm_connector *connector;
-
-       if (!fb_helper_conn)
-               return false;
-       connector = fb_helper_conn->connector;
-
-       cmdline_mode = &fb_helper_conn->cmdline_mode;
-       if (!mode_option)
-               mode_option = fb_mode_option;
-
-       if (!mode_option) {
-               cmdline_mode->specified = false;
-               return false;
-       }
-
-       name = mode_option;
-       namelen = strlen(name);
-       for (i = namelen-1; i >= 0; i--) {
-               switch (name[i]) {
-               case '@':
-                       namelen = i;
-                       if (!refresh_specified && !bpp_specified &&
-                           !yres_specified) {
-                               refresh = simple_strtol(&name[i+1], NULL, 10);
-                               refresh_specified = 1;
-                               if (cvt || rb)
-                                       cvt = 0;
-                       } else
-                               goto done;
-                       break;
-               case '-':
-                       namelen = i;
-                       if (!bpp_specified && !yres_specified) {
-                               bpp = simple_strtol(&name[i+1], NULL, 10);
-                               bpp_specified = 1;
-                               if (cvt || rb)
-                                       cvt = 0;
-                       } else
-                               goto done;
-                       break;
-               case 'x':
-                       if (!yres_specified) {
-                               yres = simple_strtol(&name[i+1], NULL, 10);
-                               yres_specified = 1;
-                       } else
-                               goto done;
-               case '0' ... '9':
-                       break;
-               case 'M':
-                       if (!yres_specified)
-                               cvt = 1;
-                       break;
-               case 'R':
-                       if (cvt)
-                               rb = 1;
-                       break;
-               case 'm':
-                       if (!cvt)
-                               margins = 1;
-                       break;
-               case 'i':
-                       if (!cvt)
-                               interlace = 1;
-                       break;
-               case 'e':
-                       force = DRM_FORCE_ON;
-                       break;
-               case 'D':
-                       if ((connector->connector_type != DRM_MODE_CONNECTOR_DVII) &&
-                           (connector->connector_type != DRM_MODE_CONNECTOR_HDMIB))
-                               force = DRM_FORCE_ON;
-                       else
-                               force = DRM_FORCE_ON_DIGITAL;
-                       break;
-               case 'd':
-                       force = DRM_FORCE_OFF;
-                       break;
-               default:
-                       goto done;
-               }
-       }
-       if (i < 0 && yres_specified) {
-               xres = simple_strtol(name, NULL, 10);
-               res_specified = 1;
-       }
-done:
-
-       DRM_DEBUG_KMS("cmdline mode for connector %s %dx%d@%dHz%s%s%s\n",
-               drm_get_connector_name(connector), xres, yres,
-               (refresh) ? refresh : 60, (rb) ? " reduced blanking" :
-               "", (margins) ? " with margins" : "", (interlace) ?
-               " interlaced" : "");
-
-       if (force) {
-               const char *s;
-               switch (force) {
-               case DRM_FORCE_OFF: s = "OFF"; break;
-               case DRM_FORCE_ON_DIGITAL: s = "ON - dig"; break;
-               default:
-               case DRM_FORCE_ON: s = "ON"; break;
-               }
-
-               DRM_INFO("forcing %s connector %s\n",
-                        drm_get_connector_name(connector), s);
-               connector->force = force;
-       }
-
-       if (res_specified) {
-               cmdline_mode->specified = true;
-               cmdline_mode->xres = xres;
-               cmdline_mode->yres = yres;
-       }
-
-       if (refresh_specified) {
-               cmdline_mode->refresh_specified = true;
-               cmdline_mode->refresh = refresh;
-       }
-
-       if (bpp_specified) {
-               cmdline_mode->bpp_specified = true;
-               cmdline_mode->bpp = bpp;
-       }
-       cmdline_mode->rb = rb ? true : false;
-       cmdline_mode->cvt = cvt  ? true : false;
-       cmdline_mode->interlace = interlace ? true : false;
-
-       return true;
-}
-
-static int drm_fb_helper_parse_command_line(struct drm_fb_helper *fb_helper)
-{
-       struct drm_fb_helper_connector *fb_helper_conn;
-       int i;
-
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               char *option = NULL;
-
-               fb_helper_conn = fb_helper->connector_info[i];
-
-               /* do something on return - turn off connector maybe */
-               if (fb_get_options(drm_get_connector_name(fb_helper_conn->connector), &option))
-                       continue;
-
-               drm_fb_helper_connector_parse_command_line(fb_helper_conn, option);
-       }
-       return 0;
-}
-
-static void drm_fb_helper_save_lut_atomic(struct drm_crtc *crtc, struct drm_fb_helper *helper)
-{
-       uint16_t *r_base, *g_base, *b_base;
-       int i;
-
-       r_base = crtc->gamma_store;
-       g_base = r_base + crtc->gamma_size;
-       b_base = g_base + crtc->gamma_size;
-
-       for (i = 0; i < crtc->gamma_size; i++)
-               helper->funcs->gamma_get(crtc, &r_base[i], &g_base[i], &b_base[i], i);
-}
-
-static void drm_fb_helper_restore_lut_atomic(struct drm_crtc *crtc)
-{
-       uint16_t *r_base, *g_base, *b_base;
-
-       r_base = crtc->gamma_store;
-       g_base = r_base + crtc->gamma_size;
-       b_base = g_base + crtc->gamma_size;
-
-       crtc->funcs->gamma_set(crtc, r_base, g_base, b_base, 0, crtc->gamma_size);
-}
-
-int drm_fb_helper_debug_enter(struct fb_info *info)
-{
-       struct drm_fb_helper *helper = info->par;
-       struct drm_crtc_helper_funcs *funcs;
-       int i;
-
-       if (list_empty(&kernel_fb_helper_list))
-               return false;
-
-       list_for_each_entry(helper, &kernel_fb_helper_list, kernel_fb_list) {
-               for (i = 0; i < helper->crtc_count; i++) {
-                       struct drm_mode_set *mode_set =
-                               &helper->crtc_info[i].mode_set;
-
-                       if (!mode_set->crtc->enabled)
-                               continue;
-
-                       funcs = mode_set->crtc->helper_private;
-                       drm_fb_helper_save_lut_atomic(mode_set->crtc, helper);
-                       funcs->mode_set_base_atomic(mode_set->crtc,
-                                                   mode_set->fb,
-                                                   mode_set->x,
-                                                   mode_set->y,
-                                                   ENTER_ATOMIC_MODE_SET);
-               }
-       }
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_fb_helper_debug_enter);
-
-/* Find the real fb for a given fb helper CRTC */
-static struct drm_framebuffer *drm_mode_config_fb(struct drm_crtc *crtc)
-{
-       struct drm_device *dev = crtc->dev;
-       struct drm_crtc *c;
-
-       list_for_each_entry(c, &dev->mode_config.crtc_list, head) {
-               if (crtc->base.id == c->base.id)
-                       return c->fb;
-       }
-
-       return NULL;
-}
-
-int drm_fb_helper_debug_leave(struct fb_info *info)
-{
-       struct drm_fb_helper *helper = info->par;
-       struct drm_crtc *crtc;
-       struct drm_crtc_helper_funcs *funcs;
-       struct drm_framebuffer *fb;
-       int i;
-
-       for (i = 0; i < helper->crtc_count; i++) {
-               struct drm_mode_set *mode_set = &helper->crtc_info[i].mode_set;
-               crtc = mode_set->crtc;
-               funcs = crtc->helper_private;
-               fb = drm_mode_config_fb(crtc);
-
-               if (!crtc->enabled)
-                       continue;
-
-               if (!fb) {
-                       DRM_ERROR("no fb to restore??\n");
-                       continue;
-               }
-
-               drm_fb_helper_restore_lut_atomic(mode_set->crtc);
-               funcs->mode_set_base_atomic(mode_set->crtc, fb, crtc->x,
-                                           crtc->y, LEAVE_ATOMIC_MODE_SET);
-       }
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_fb_helper_debug_leave);
-
-bool drm_fb_helper_force_kernel_mode(void)
-{
-       int i = 0;
-       bool ret, error = false;
-       struct drm_fb_helper *helper;
-
-       if (list_empty(&kernel_fb_helper_list))
-               return false;
-
-       list_for_each_entry(helper, &kernel_fb_helper_list, kernel_fb_list) {
-               for (i = 0; i < helper->crtc_count; i++) {
-                       struct drm_mode_set *mode_set = &helper->crtc_info[i].mode_set;
-                       ret = drm_crtc_helper_set_config(mode_set);
-                       if (ret)
-                               error = true;
-               }
-       }
-       return error;
-}
-
-int drm_fb_helper_panic(struct notifier_block *n, unsigned long ununsed,
-                       void *panic_str)
-{
-       printk(KERN_ERR "panic occurred, switching back to text console\n");
-       return drm_fb_helper_force_kernel_mode();
-       return 0;
-}
-EXPORT_SYMBOL(drm_fb_helper_panic);
-
-static struct notifier_block paniced = {
-       .notifier_call = drm_fb_helper_panic,
-};
-
-/**
- * drm_fb_helper_restore - restore the framebuffer console (kernel) config
- *
- * Restore's the kernel's fbcon mode, used for lastclose & panic paths.
- */
-void drm_fb_helper_restore(void)
-{
-       bool ret;
-       ret = drm_fb_helper_force_kernel_mode();
-       if (ret == true)
-               DRM_ERROR("Failed to restore crtc configuration\n");
-}
-EXPORT_SYMBOL(drm_fb_helper_restore);
-
-#ifdef CONFIG_MAGIC_SYSRQ
-static void drm_fb_helper_restore_work_fn(struct work_struct *ignored)
-{
-       drm_fb_helper_restore();
-}
-static DECLARE_WORK(drm_fb_helper_restore_work, drm_fb_helper_restore_work_fn);
-
-static void drm_fb_helper_sysrq(int dummy1)
-{
-       schedule_work(&drm_fb_helper_restore_work);
-}
-
-static struct sysrq_key_op sysrq_drm_fb_helper_restore_op = {
-       .handler = drm_fb_helper_sysrq,
-       .help_msg = "force-fb(V)",
-       .action_msg = "Restore framebuffer console",
-};
-#else
-static struct sysrq_key_op sysrq_drm_fb_helper_restore_op = { };
-#endif
-
-static void drm_fb_helper_on(struct fb_info *info)
-{
-       struct drm_fb_helper *fb_helper = info->par;
-       struct drm_device *dev = fb_helper->dev;
-       struct drm_crtc *crtc;
-       struct drm_crtc_helper_funcs *crtc_funcs;
-       struct drm_connector *connector;
-       struct drm_encoder *encoder;
-       int i, j;
-
-       /*
-        * For each CRTC in this fb, turn the crtc on then,
-        * find all associated encoders and turn them on.
-        */
-       mutex_lock(&dev->mode_config.mutex);
-       for (i = 0; i < fb_helper->crtc_count; i++) {
-               crtc = fb_helper->crtc_info[i].mode_set.crtc;
-               crtc_funcs = crtc->helper_private;
-
-               if (!crtc->enabled)
-                       continue;
-
-               crtc_funcs->dpms(crtc, DRM_MODE_DPMS_ON);
-
-               /* Walk the connectors & encoders on this fb turning them on */
-               for (j = 0; j < fb_helper->connector_count; j++) {
-                       connector = fb_helper->connector_info[j]->connector;
-                       connector->dpms = DRM_MODE_DPMS_ON;
-                       drm_connector_property_set_value(connector,
-                                                        dev->mode_config.dpms_property,
-                                                        DRM_MODE_DPMS_ON);
-               }
-               /* Found a CRTC on this fb, now find encoders */
-               list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-                       if (encoder->crtc == crtc) {
-                               struct drm_encoder_helper_funcs *encoder_funcs;
-
-                               encoder_funcs = encoder->helper_private;
-                               encoder_funcs->dpms(encoder, DRM_MODE_DPMS_ON);
-                       }
-               }
-       }
-       mutex_unlock(&dev->mode_config.mutex);
-}
-
-static void drm_fb_helper_off(struct fb_info *info, int dpms_mode)
-{
-       struct drm_fb_helper *fb_helper = info->par;
-       struct drm_device *dev = fb_helper->dev;
-       struct drm_crtc *crtc;
-       struct drm_crtc_helper_funcs *crtc_funcs;
-       struct drm_connector *connector;
-       struct drm_encoder *encoder;
-       int i, j;
-
-       /*
-        * For each CRTC in this fb, find all associated encoders
-        * and turn them off, then turn off the CRTC.
-        */
-       mutex_lock(&dev->mode_config.mutex);
-       for (i = 0; i < fb_helper->crtc_count; i++) {
-               crtc = fb_helper->crtc_info[i].mode_set.crtc;
-               crtc_funcs = crtc->helper_private;
-
-               if (!crtc->enabled)
-                       continue;
-
-               /* Walk the connectors on this fb and mark them off */
-               for (j = 0; j < fb_helper->connector_count; j++) {
-                       connector = fb_helper->connector_info[j]->connector;
-                       connector->dpms = dpms_mode;
-                       drm_connector_property_set_value(connector,
-                                                        dev->mode_config.dpms_property,
-                                                        dpms_mode);
-               }
-               /* Found a CRTC on this fb, now find encoders */
-               list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-                       if (encoder->crtc == crtc) {
-                               struct drm_encoder_helper_funcs *encoder_funcs;
-
-                               encoder_funcs = encoder->helper_private;
-                               encoder_funcs->dpms(encoder, dpms_mode);
-                       }
-               }
-               crtc_funcs->dpms(crtc, DRM_MODE_DPMS_OFF);
-       }
-       mutex_unlock(&dev->mode_config.mutex);
-}
-
-int drm_fb_helper_blank(int blank, struct fb_info *info)
-{
-       switch (blank) {
-       /* Display: On; HSync: On, VSync: On */
-       case FB_BLANK_UNBLANK:
-               drm_fb_helper_on(info);
-               break;
-       /* Display: Off; HSync: On, VSync: On */
-       case FB_BLANK_NORMAL:
-               drm_fb_helper_off(info, DRM_MODE_DPMS_STANDBY);
-               break;
-       /* Display: Off; HSync: Off, VSync: On */
-       case FB_BLANK_HSYNC_SUSPEND:
-               drm_fb_helper_off(info, DRM_MODE_DPMS_STANDBY);
-               break;
-       /* Display: Off; HSync: On, VSync: Off */
-       case FB_BLANK_VSYNC_SUSPEND:
-               drm_fb_helper_off(info, DRM_MODE_DPMS_SUSPEND);
-               break;
-       /* Display: Off; HSync: Off, VSync: Off */
-       case FB_BLANK_POWERDOWN:
-               drm_fb_helper_off(info, DRM_MODE_DPMS_OFF);
-               break;
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_fb_helper_blank);
-
-static void drm_fb_helper_crtc_free(struct drm_fb_helper *helper)
-{
-       int i;
-
-       for (i = 0; i < helper->connector_count; i++)
-               kfree(helper->connector_info[i]);
-       kfree(helper->connector_info);
-       for (i = 0; i < helper->crtc_count; i++)
-               kfree(helper->crtc_info[i].mode_set.connectors);
-       kfree(helper->crtc_info);
-}
-
-int drm_fb_helper_init(struct drm_device *dev,
-                      struct drm_fb_helper *fb_helper,
-                      int crtc_count, int max_conn_count)
-{
-       struct drm_crtc *crtc;
-       int ret = 0;
-       int i;
-
-       fb_helper->dev = dev;
-
-       INIT_LIST_HEAD(&fb_helper->kernel_fb_list);
-
-       fb_helper->crtc_info = kcalloc(crtc_count, sizeof(struct drm_fb_helper_crtc), GFP_KERNEL);
-       if (!fb_helper->crtc_info)
-               return -ENOMEM;
-
-       fb_helper->crtc_count = crtc_count;
-       fb_helper->connector_info = kcalloc(dev->mode_config.num_connector, sizeof(struct drm_fb_helper_connector *), GFP_KERNEL);
-       if (!fb_helper->connector_info) {
-               kfree(fb_helper->crtc_info);
-               return -ENOMEM;
-       }
-       fb_helper->connector_count = 0;
-
-       for (i = 0; i < crtc_count; i++) {
-               fb_helper->crtc_info[i].mode_set.connectors =
-                       kcalloc(max_conn_count,
-                               sizeof(struct drm_connector *),
-                               GFP_KERNEL);
-
-               if (!fb_helper->crtc_info[i].mode_set.connectors) {
-                       ret = -ENOMEM;
-                       goto out_free;
-               }
-               fb_helper->crtc_info[i].mode_set.num_connectors = 0;
-       }
-
-       i = 0;
-       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
-               fb_helper->crtc_info[i].crtc_id = crtc->base.id;
-               fb_helper->crtc_info[i].mode_set.crtc = crtc;
-               i++;
-       }
-       fb_helper->conn_limit = max_conn_count;
-       return 0;
-out_free:
-       drm_fb_helper_crtc_free(fb_helper);
-       return -ENOMEM;
-}
-EXPORT_SYMBOL(drm_fb_helper_init);
-
-void drm_fb_helper_fini(struct drm_fb_helper *fb_helper)
-{
-       if (!list_empty(&fb_helper->kernel_fb_list)) {
-               list_del(&fb_helper->kernel_fb_list);
-               if (list_empty(&kernel_fb_helper_list)) {
-                       printk(KERN_INFO "drm: unregistered panic notifier\n");
-                       atomic_notifier_chain_unregister(&panic_notifier_list,
-                                                        &paniced);
-                       unregister_sysrq_key('v', &sysrq_drm_fb_helper_restore_op);
-               }
-       }
-
-       drm_fb_helper_crtc_free(fb_helper);
-
-}
-EXPORT_SYMBOL(drm_fb_helper_fini);
-
-static int setcolreg(struct drm_crtc *crtc, u16 red, u16 green,
-                    u16 blue, u16 regno, struct fb_info *info)
-{
-       struct drm_fb_helper *fb_helper = info->par;
-       struct drm_framebuffer *fb = fb_helper->fb;
-       int pindex;
-
-       if (info->fix.visual == FB_VISUAL_TRUECOLOR) {
-               u32 *palette;
-               u32 value;
-               /* place color in psuedopalette */
-               if (regno > 16)
-                       return -EINVAL;
-               palette = (u32 *)info->pseudo_palette;
-               red >>= (16 - info->var.red.length);
-               green >>= (16 - info->var.green.length);
-               blue >>= (16 - info->var.blue.length);
-               value = (red << info->var.red.offset) |
-                       (green << info->var.green.offset) |
-                       (blue << info->var.blue.offset);
-               palette[regno] = value;
-               return 0;
-       }
-
-       pindex = regno;
-
-       if (fb->bits_per_pixel == 16) {
-               pindex = regno << 3;
-
-               if (fb->depth == 16 && regno > 63)
-                       return -EINVAL;
-               if (fb->depth == 15 && regno > 31)
-                       return -EINVAL;
-
-               if (fb->depth == 16) {
-                       u16 r, g, b;
-                       int i;
-                       if (regno < 32) {
-                               for (i = 0; i < 8; i++)
-                                       fb_helper->funcs->gamma_set(crtc, red,
-                                               green, blue, pindex + i);
-                       }
-
-                       fb_helper->funcs->gamma_get(crtc, &r,
-                                                   &g, &b,
-                                                   pindex >> 1);
-
-                       for (i = 0; i < 4; i++)
-                               fb_helper->funcs->gamma_set(crtc, r,
-                                                           green, b,
-                                                           (pindex >> 1) + i);
-               }
-       }
-
-       if (fb->depth != 16)
-               fb_helper->funcs->gamma_set(crtc, red, green, blue, pindex);
-       return 0;
-}
-
-int drm_fb_helper_setcmap(struct fb_cmap *cmap, struct fb_info *info)
-{
-       struct drm_fb_helper *fb_helper = info->par;
-       struct drm_crtc_helper_funcs *crtc_funcs;
-       u16 *red, *green, *blue, *transp;
-       struct drm_crtc *crtc;
-       int i, rc = 0;
-       int start;
-
-       for (i = 0; i < fb_helper->crtc_count; i++) {
-               crtc = fb_helper->crtc_info[i].mode_set.crtc;
-               crtc_funcs = crtc->helper_private;
-
-               red = cmap->red;
-               green = cmap->green;
-               blue = cmap->blue;
-               transp = cmap->transp;
-               start = cmap->start;
-
-               for (i = 0; i < cmap->len; i++) {
-                       u16 hred, hgreen, hblue, htransp = 0xffff;
-
-                       hred = *red++;
-                       hgreen = *green++;
-                       hblue = *blue++;
-
-                       if (transp)
-                               htransp = *transp++;
-
-                       rc = setcolreg(crtc, hred, hgreen, hblue, start++, info);
-                       if (rc)
-                               return rc;
-               }
-               crtc_funcs->load_lut(crtc);
-       }
-       return rc;
-}
-EXPORT_SYMBOL(drm_fb_helper_setcmap);
-
-int drm_fb_helper_check_var(struct fb_var_screeninfo *var,
-                           struct fb_info *info)
-{
-       struct drm_fb_helper *fb_helper = info->par;
-       struct drm_framebuffer *fb = fb_helper->fb;
-       int depth;
-
-       if (var->pixclock != 0 || in_dbg_master())
-               return -EINVAL;
-
-       /* Need to resize the fb object !!! */
-       if (var->bits_per_pixel > fb->bits_per_pixel || var->xres > fb->width || var->yres > fb->height) {
-               DRM_DEBUG("fb userspace requested width/height/bpp is greater than current fb "
-                         "object %dx%d-%d > %dx%d-%d\n", var->xres, var->yres, var->bits_per_pixel,
-                         fb->width, fb->height, fb->bits_per_pixel);
-               return -EINVAL;
-       }
-
-       switch (var->bits_per_pixel) {
-       case 16:
-               depth = (var->green.length == 6) ? 16 : 15;
-               break;
-       case 32:
-               depth = (var->transp.length > 0) ? 32 : 24;
-               break;
-       default:
-               depth = var->bits_per_pixel;
-               break;
-       }
-
-       switch (depth) {
-       case 8:
-               var->red.offset = 0;
-               var->green.offset = 0;
-               var->blue.offset = 0;
-               var->red.length = 8;
-               var->green.length = 8;
-               var->blue.length = 8;
-               var->transp.length = 0;
-               var->transp.offset = 0;
-               break;
-       case 15:
-               var->red.offset = 10;
-               var->green.offset = 5;
-               var->blue.offset = 0;
-               var->red.length = 5;
-               var->green.length = 5;
-               var->blue.length = 5;
-               var->transp.length = 1;
-               var->transp.offset = 15;
-               break;
-       case 16:
-               var->red.offset = 11;
-               var->green.offset = 5;
-               var->blue.offset = 0;
-               var->red.length = 5;
-               var->green.length = 6;
-               var->blue.length = 5;
-               var->transp.length = 0;
-               var->transp.offset = 0;
-               break;
-       case 24:
-               var->red.offset = 16;
-               var->green.offset = 8;
-               var->blue.offset = 0;
-               var->red.length = 8;
-               var->green.length = 8;
-               var->blue.length = 8;
-               var->transp.length = 0;
-               var->transp.offset = 0;
-               break;
-       case 32:
-               var->red.offset = 16;
-               var->green.offset = 8;
-               var->blue.offset = 0;
-               var->red.length = 8;
-               var->green.length = 8;
-               var->blue.length = 8;
-               var->transp.length = 8;
-               var->transp.offset = 24;
-               break;
-       default:
-               return -EINVAL;
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_fb_helper_check_var);
-
-/* this will let fbcon do the mode init */
-int drm_fb_helper_set_par(struct fb_info *info)
-{
-       struct drm_fb_helper *fb_helper = info->par;
-       struct drm_device *dev = fb_helper->dev;
-       struct fb_var_screeninfo *var = &info->var;
-       struct drm_crtc *crtc;
-       int ret;
-       int i;
-
-       if (var->pixclock != 0) {
-               DRM_ERROR("PIXEL CLOCK SET\n");
-               return -EINVAL;
-       }
-
-       mutex_lock(&dev->mode_config.mutex);
-       for (i = 0; i < fb_helper->crtc_count; i++) {
-               crtc = fb_helper->crtc_info[i].mode_set.crtc;
-               ret = crtc->funcs->set_config(&fb_helper->crtc_info[i].mode_set);
-               if (ret) {
-                       mutex_unlock(&dev->mode_config.mutex);
-                       return ret;
-               }
-       }
-       mutex_unlock(&dev->mode_config.mutex);
-
-       if (fb_helper->delayed_hotplug) {
-               fb_helper->delayed_hotplug = false;
-               drm_fb_helper_hotplug_event(fb_helper);
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_fb_helper_set_par);
-
-int drm_fb_helper_pan_display(struct fb_var_screeninfo *var,
-                             struct fb_info *info)
-{
-       struct drm_fb_helper *fb_helper = info->par;
-       struct drm_device *dev = fb_helper->dev;
-       struct drm_mode_set *modeset;
-       struct drm_crtc *crtc;
-       int ret = 0;
-       int i;
-
-       mutex_lock(&dev->mode_config.mutex);
-       for (i = 0; i < fb_helper->crtc_count; i++) {
-               crtc = fb_helper->crtc_info[i].mode_set.crtc;
-
-               modeset = &fb_helper->crtc_info[i].mode_set;
-
-               modeset->x = var->xoffset;
-               modeset->y = var->yoffset;
-
-               if (modeset->num_connectors) {
-                       ret = crtc->funcs->set_config(modeset);
-                       if (!ret) {
-                               info->var.xoffset = var->xoffset;
-                               info->var.yoffset = var->yoffset;
-                       }
-               }
-       }
-       mutex_unlock(&dev->mode_config.mutex);
-       return ret;
-}
-EXPORT_SYMBOL(drm_fb_helper_pan_display);
-
-int drm_fb_helper_single_fb_probe(struct drm_fb_helper *fb_helper,
-                                 int preferred_bpp)
-{
-       int new_fb = 0;
-       int crtc_count = 0;
-       int i;
-       struct fb_info *info;
-       struct drm_fb_helper_surface_size sizes;
-       int gamma_size = 0;
-
-       memset(&sizes, 0, sizeof(struct drm_fb_helper_surface_size));
-       sizes.surface_depth = 24;
-       sizes.surface_bpp = 32;
-       sizes.fb_width = (unsigned)-1;
-       sizes.fb_height = (unsigned)-1;
-
-       /* if driver picks 8 or 16 by default use that
-          for both depth/bpp */
-       if (preferred_bpp != sizes.surface_bpp) {
-               sizes.surface_depth = sizes.surface_bpp = preferred_bpp;
-       }
-       /* first up get a count of crtcs now in use and new min/maxes width/heights */
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               struct drm_fb_helper_connector *fb_helper_conn = fb_helper->connector_info[i];
-               struct drm_fb_helper_cmdline_mode *cmdline_mode;
-
-               cmdline_mode = &fb_helper_conn->cmdline_mode;
-
-               if (cmdline_mode->bpp_specified) {
-                       switch (cmdline_mode->bpp) {
-                       case 8:
-                               sizes.surface_depth = sizes.surface_bpp = 8;
-                               break;
-                       case 15:
-                               sizes.surface_depth = 15;
-                               sizes.surface_bpp = 16;
-                               break;
-                       case 16:
-                               sizes.surface_depth = sizes.surface_bpp = 16;
-                               break;
-                       case 24:
-                               sizes.surface_depth = sizes.surface_bpp = 24;
-                               break;
-                       case 32:
-                               sizes.surface_depth = 24;
-                               sizes.surface_bpp = 32;
-                               break;
-                       }
-                       break;
-               }
-       }
-
-       crtc_count = 0;
-       for (i = 0; i < fb_helper->crtc_count; i++) {
-               struct drm_display_mode *desired_mode;
-               desired_mode = fb_helper->crtc_info[i].desired_mode;
-
-               if (desired_mode) {
-                       if (gamma_size == 0)
-                               gamma_size = fb_helper->crtc_info[i].mode_set.crtc->gamma_size;
-                       if (desired_mode->hdisplay < sizes.fb_width)
-                               sizes.fb_width = desired_mode->hdisplay;
-                       if (desired_mode->vdisplay < sizes.fb_height)
-                               sizes.fb_height = desired_mode->vdisplay;
-                       if (desired_mode->hdisplay > sizes.surface_width)
-                               sizes.surface_width = desired_mode->hdisplay;
-                       if (desired_mode->vdisplay > sizes.surface_height)
-                               sizes.surface_height = desired_mode->vdisplay;
-                       crtc_count++;
-               }
-       }
-
-       if (crtc_count == 0 || sizes.fb_width == -1 || sizes.fb_height == -1) {
-               /* hmm everyone went away - assume VGA cable just fell out
-                  and will come back later. */
-               DRM_INFO("Cannot find any crtc or sizes - going 1024x768\n");
-               sizes.fb_width = sizes.surface_width = 1024;
-               sizes.fb_height = sizes.surface_height = 768;
-       }
-
-       /* push down into drivers */
-       new_fb = (*fb_helper->funcs->fb_probe)(fb_helper, &sizes);
-       if (new_fb < 0)
-               return new_fb;
-
-       info = fb_helper->fbdev;
-
-       /* set the fb pointer */
-       for (i = 0; i < fb_helper->crtc_count; i++) {
-               fb_helper->crtc_info[i].mode_set.fb = fb_helper->fb;
-       }
-
-       if (new_fb) {
-               info->var.pixclock = 0;
-               if (register_framebuffer(info) < 0) {
-                       return -EINVAL;
-               }
-
-               printk(KERN_INFO "fb%d: %s frame buffer device\n", info->node,
-                      info->fix.id);
-
-       } else {
-               drm_fb_helper_set_par(info);
-       }
-
-       /* Switch back to kernel console on panic */
-       /* multi card linked list maybe */
-       if (list_empty(&kernel_fb_helper_list)) {
-               printk(KERN_INFO "drm: registered panic notifier\n");
-               atomic_notifier_chain_register(&panic_notifier_list,
-                                              &paniced);
-               register_sysrq_key('v', &sysrq_drm_fb_helper_restore_op);
-       }
-       if (new_fb)
-               list_add(&fb_helper->kernel_fb_list, &kernel_fb_helper_list);
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_fb_helper_single_fb_probe);
-
-void drm_fb_helper_fill_fix(struct fb_info *info, uint32_t pitch,
-                           uint32_t depth)
-{
-       info->fix.type = FB_TYPE_PACKED_PIXELS;
-       info->fix.visual = depth == 8 ? FB_VISUAL_PSEUDOCOLOR :
-               FB_VISUAL_TRUECOLOR;
-       info->fix.type_aux = 0;
-       info->fix.xpanstep = 1; /* doing it in hw */
-       info->fix.ypanstep = 1; /* doing it in hw */
-       info->fix.ywrapstep = 0;
-       info->fix.accel = FB_ACCEL_NONE;
-       info->fix.type_aux = 0;
-
-       info->fix.line_length = pitch;
-       return;
-}
-EXPORT_SYMBOL(drm_fb_helper_fill_fix);
-
-void drm_fb_helper_fill_var(struct fb_info *info, struct drm_fb_helper *fb_helper,
-                           uint32_t fb_width, uint32_t fb_height)
-{
-       struct drm_framebuffer *fb = fb_helper->fb;
-       info->pseudo_palette = fb_helper->pseudo_palette;
-       info->var.xres_virtual = fb->width;
-       info->var.yres_virtual = fb->height;
-       info->var.bits_per_pixel = fb->bits_per_pixel;
-       info->var.xoffset = 0;
-       info->var.yoffset = 0;
-       info->var.activate = FB_ACTIVATE_NOW;
-       info->var.height = -1;
-       info->var.width = -1;
-
-       switch (fb->depth) {
-       case 8:
-               info->var.red.offset = 0;
-               info->var.green.offset = 0;
-               info->var.blue.offset = 0;
-               info->var.red.length = 8; /* 8bit DAC */
-               info->var.green.length = 8;
-               info->var.blue.length = 8;
-               info->var.transp.offset = 0;
-               info->var.transp.length = 0;
-               break;
-       case 15:
-               info->var.red.offset = 10;
-               info->var.green.offset = 5;
-               info->var.blue.offset = 0;
-               info->var.red.length = 5;
-               info->var.green.length = 5;
-               info->var.blue.length = 5;
-               info->var.transp.offset = 15;
-               info->var.transp.length = 1;
-               break;
-       case 16:
-               info->var.red.offset = 11;
-               info->var.green.offset = 5;
-               info->var.blue.offset = 0;
-               info->var.red.length = 5;
-               info->var.green.length = 6;
-               info->var.blue.length = 5;
-               info->var.transp.offset = 0;
-               break;
-       case 24:
-               info->var.red.offset = 16;
-               info->var.green.offset = 8;
-               info->var.blue.offset = 0;
-               info->var.red.length = 8;
-               info->var.green.length = 8;
-               info->var.blue.length = 8;
-               info->var.transp.offset = 0;
-               info->var.transp.length = 0;
-               break;
-       case 32:
-               info->var.red.offset = 16;
-               info->var.green.offset = 8;
-               info->var.blue.offset = 0;
-               info->var.red.length = 8;
-               info->var.green.length = 8;
-               info->var.blue.length = 8;
-               info->var.transp.offset = 24;
-               info->var.transp.length = 8;
-               break;
-       default:
-               break;
-       }
-
-       info->var.xres = fb_width;
-       info->var.yres = fb_height;
-}
-EXPORT_SYMBOL(drm_fb_helper_fill_var);
-
-static int drm_fb_helper_probe_connector_modes(struct drm_fb_helper *fb_helper,
-                                              uint32_t maxX,
-                                              uint32_t maxY)
-{
-       struct drm_connector *connector;
-       int count = 0;
-       int i;
-
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               connector = fb_helper->connector_info[i]->connector;
-               count += connector->funcs->fill_modes(connector, maxX, maxY);
-       }
-
-       return count;
-}
-
-static struct drm_display_mode *drm_has_preferred_mode(struct drm_fb_helper_connector *fb_connector, int width, int height)
-{
-       struct drm_display_mode *mode;
-
-       list_for_each_entry(mode, &fb_connector->connector->modes, head) {
-               if (drm_mode_width(mode) > width ||
-                   drm_mode_height(mode) > height)
-                       continue;
-               if (mode->type & DRM_MODE_TYPE_PREFERRED)
-                       return mode;
-       }
-       return NULL;
-}
-
-static bool drm_has_cmdline_mode(struct drm_fb_helper_connector *fb_connector)
-{
-       struct drm_fb_helper_cmdline_mode *cmdline_mode;
-       cmdline_mode = &fb_connector->cmdline_mode;
-       return cmdline_mode->specified;
-}
-
-static struct drm_display_mode *drm_pick_cmdline_mode(struct drm_fb_helper_connector *fb_helper_conn,
-                                                     int width, int height)
-{
-       struct drm_fb_helper_cmdline_mode *cmdline_mode;
-       struct drm_display_mode *mode = NULL;
-
-       cmdline_mode = &fb_helper_conn->cmdline_mode;
-       if (cmdline_mode->specified == false)
-               return mode;
-
-       /* attempt to find a matching mode in the list of modes
-        *  we have gotten so far, if not add a CVT mode that conforms
-        */
-       if (cmdline_mode->rb || cmdline_mode->margins)
-               goto create_mode;
-
-       list_for_each_entry(mode, &fb_helper_conn->connector->modes, head) {
-               /* check width/height */
-               if (mode->hdisplay != cmdline_mode->xres ||
-                   mode->vdisplay != cmdline_mode->yres)
-                       continue;
-
-               if (cmdline_mode->refresh_specified) {
-                       if (mode->vrefresh != cmdline_mode->refresh)
-                               continue;
-               }
-
-               if (cmdline_mode->interlace) {
-                       if (!(mode->flags & DRM_MODE_FLAG_INTERLACE))
-                               continue;
-               }
-               return mode;
-       }
-
-create_mode:
-       if (cmdline_mode->cvt)
-               mode = drm_cvt_mode(fb_helper_conn->connector->dev,
-                                   cmdline_mode->xres, cmdline_mode->yres,
-                                   cmdline_mode->refresh_specified ? cmdline_mode->refresh : 60,
-                                   cmdline_mode->rb, cmdline_mode->interlace,
-                                   cmdline_mode->margins);
-       else
-               mode = drm_gtf_mode(fb_helper_conn->connector->dev,
-                                   cmdline_mode->xres, cmdline_mode->yres,
-                                   cmdline_mode->refresh_specified ? cmdline_mode->refresh : 60,
-                                   cmdline_mode->interlace,
-                                   cmdline_mode->margins);
-       drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
-       list_add(&mode->head, &fb_helper_conn->connector->modes);
-       return mode;
-}
-
-static bool drm_connector_enabled(struct drm_connector *connector, bool strict)
-{
-       bool enable;
-
-       if (strict) {
-               enable = connector->status == connector_status_connected;
-       } else {
-               enable = connector->status != connector_status_disconnected;
-       }
-       return enable;
-}
-
-static void drm_enable_connectors(struct drm_fb_helper *fb_helper,
-                                 bool *enabled)
-{
-       bool any_enabled = false;
-       struct drm_connector *connector;
-       int i = 0;
-
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               connector = fb_helper->connector_info[i]->connector;
-               enabled[i] = drm_connector_enabled(connector, true);
-               DRM_DEBUG_KMS("connector %d enabled? %s\n", connector->base.id,
-                         enabled[i] ? "yes" : "no");
-               any_enabled |= enabled[i];
-       }
-
-       if (any_enabled)
-               return;
-
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               connector = fb_helper->connector_info[i]->connector;
-               enabled[i] = drm_connector_enabled(connector, false);
-       }
-}
-
-static bool drm_target_cloned(struct drm_fb_helper *fb_helper,
-                             struct drm_display_mode **modes,
-                             bool *enabled, int width, int height)
-{
-       int count, i, j;
-       bool can_clone = false;
-       struct drm_fb_helper_connector *fb_helper_conn;
-       struct drm_display_mode *dmt_mode, *mode;
-
-       /* only contemplate cloning in the single crtc case */
-       if (fb_helper->crtc_count > 1)
-               return false;
-
-       count = 0;
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               if (enabled[i])
-                       count++;
-       }
-
-       /* only contemplate cloning if more than one connector is enabled */
-       if (count <= 1)
-               return false;
-
-       /* check the command line or if nothing common pick 1024x768 */
-       can_clone = true;
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               if (!enabled[i])
-                       continue;
-               fb_helper_conn = fb_helper->connector_info[i];
-               modes[i] = drm_pick_cmdline_mode(fb_helper_conn, width, height);
-               if (!modes[i]) {
-                       can_clone = false;
-                       break;
-               }
-               for (j = 0; j < i; j++) {
-                       if (!enabled[j])
-                               continue;
-                       if (!drm_mode_equal(modes[j], modes[i]))
-                               can_clone = false;
-               }
-       }
-
-       if (can_clone) {
-               DRM_DEBUG_KMS("can clone using command line\n");
-               return true;
-       }
-
-       /* try and find a 1024x768 mode on each connector */
-       can_clone = true;
-       dmt_mode = drm_mode_find_dmt(fb_helper->dev, 1024, 768, 60);
-
-       for (i = 0; i < fb_helper->connector_count; i++) {
-
-               if (!enabled[i])
-                       continue;
-
-               fb_helper_conn = fb_helper->connector_info[i];
-               list_for_each_entry(mode, &fb_helper_conn->connector->modes, head) {
-                       if (drm_mode_equal(mode, dmt_mode))
-                               modes[i] = mode;
-               }
-               if (!modes[i])
-                       can_clone = false;
-       }
-
-       if (can_clone) {
-               DRM_DEBUG_KMS("can clone using 1024x768\n");
-               return true;
-       }
-       DRM_INFO("kms: can't enable cloning when we probably wanted to.\n");
-       return false;
-}
-
-static bool drm_target_preferred(struct drm_fb_helper *fb_helper,
-                                struct drm_display_mode **modes,
-                                bool *enabled, int width, int height)
-{
-       struct drm_fb_helper_connector *fb_helper_conn;
-       int i;
-
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               fb_helper_conn = fb_helper->connector_info[i];
-
-               if (enabled[i] == false)
-                       continue;
-
-               DRM_DEBUG_KMS("looking for cmdline mode on connector %d\n",
-                             fb_helper_conn->connector->base.id);
-
-               /* got for command line mode first */
-               modes[i] = drm_pick_cmdline_mode(fb_helper_conn, width, height);
-               if (!modes[i]) {
-                       DRM_DEBUG_KMS("looking for preferred mode on connector %d\n",
-                                     fb_helper_conn->connector->base.id);
-                       modes[i] = drm_has_preferred_mode(fb_helper_conn, width, height);
-               }
-               /* No preferred modes, pick one off the list */
-               if (!modes[i] && !list_empty(&fb_helper_conn->connector->modes)) {
-                       list_for_each_entry(modes[i], &fb_helper_conn->connector->modes, head)
-                               break;
-               }
-               DRM_DEBUG_KMS("found mode %s\n", modes[i] ? modes[i]->name :
-                         "none");
-       }
-       return true;
-}
-
-static int drm_pick_crtcs(struct drm_fb_helper *fb_helper,
-                         struct drm_fb_helper_crtc **best_crtcs,
-                         struct drm_display_mode **modes,
-                         int n, int width, int height)
-{
-       int c, o;
-       struct drm_device *dev = fb_helper->dev;
-       struct drm_connector *connector;
-       struct drm_connector_helper_funcs *connector_funcs;
-       struct drm_encoder *encoder;
-       struct drm_fb_helper_crtc *best_crtc;
-       int my_score, best_score, score;
-       struct drm_fb_helper_crtc **crtcs, *crtc;
-       struct drm_fb_helper_connector *fb_helper_conn;
-
-       if (n == fb_helper->connector_count)
-               return 0;
-
-       fb_helper_conn = fb_helper->connector_info[n];
-       connector = fb_helper_conn->connector;
-
-       best_crtcs[n] = NULL;
-       best_crtc = NULL;
-       best_score = drm_pick_crtcs(fb_helper, best_crtcs, modes, n+1, width, height);
-       if (modes[n] == NULL)
-               return best_score;
-
-       crtcs = kzalloc(dev->mode_config.num_connector *
-                       sizeof(struct drm_fb_helper_crtc *), GFP_KERNEL);
-       if (!crtcs)
-               return best_score;
-
-       my_score = 1;
-       if (connector->status == connector_status_connected)
-               my_score++;
-       if (drm_has_cmdline_mode(fb_helper_conn))
-               my_score++;
-       if (drm_has_preferred_mode(fb_helper_conn, width, height))
-               my_score++;
-
-       connector_funcs = connector->helper_private;
-       encoder = connector_funcs->best_encoder(connector);
-       if (!encoder)
-               goto out;
-
-       /* select a crtc for this connector and then attempt to configure
-          remaining connectors */
-       for (c = 0; c < fb_helper->crtc_count; c++) {
-               crtc = &fb_helper->crtc_info[c];
-
-               if ((encoder->possible_crtcs & (1 << c)) == 0) {
-                       continue;
-               }
-
-               for (o = 0; o < n; o++)
-                       if (best_crtcs[o] == crtc)
-                               break;
-
-               if (o < n) {
-                       /* ignore cloning unless only a single crtc */
-                       if (fb_helper->crtc_count > 1)
-                               continue;
-
-                       if (!drm_mode_equal(modes[o], modes[n]))
-                               continue;
-               }
-
-               crtcs[n] = crtc;
-               memcpy(crtcs, best_crtcs, n * sizeof(struct drm_fb_helper_crtc *));
-               score = my_score + drm_pick_crtcs(fb_helper, crtcs, modes, n + 1,
-                                                 width, height);
-               if (score > best_score) {
-                       best_crtc = crtc;
-                       best_score = score;
-                       memcpy(best_crtcs, crtcs,
-                              dev->mode_config.num_connector *
-                              sizeof(struct drm_fb_helper_crtc *));
-               }
-       }
-out:
-       kfree(crtcs);
-       return best_score;
-}
-
-static void drm_setup_crtcs(struct drm_fb_helper *fb_helper)
-{
-       struct drm_device *dev = fb_helper->dev;
-       struct drm_fb_helper_crtc **crtcs;
-       struct drm_display_mode **modes;
-       struct drm_encoder *encoder;
-       struct drm_mode_set *modeset;
-       bool *enabled;
-       int width, height;
-       int i, ret;
-
-       DRM_DEBUG_KMS("\n");
-
-       width = dev->mode_config.max_width;
-       height = dev->mode_config.max_height;
-
-       /* clean out all the encoder/crtc combos */
-       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
-               encoder->crtc = NULL;
-       }
-
-       crtcs = kcalloc(dev->mode_config.num_connector,
-                       sizeof(struct drm_fb_helper_crtc *), GFP_KERNEL);
-       modes = kcalloc(dev->mode_config.num_connector,
-                       sizeof(struct drm_display_mode *), GFP_KERNEL);
-       enabled = kcalloc(dev->mode_config.num_connector,
-                         sizeof(bool), GFP_KERNEL);
-
-       drm_enable_connectors(fb_helper, enabled);
-
-       ret = drm_target_cloned(fb_helper, modes, enabled, width, height);
-       if (!ret) {
-               ret = drm_target_preferred(fb_helper, modes, enabled, width, height);
-               if (!ret)
-                       DRM_ERROR("Unable to find initial modes\n");
-       }
-
-       DRM_DEBUG_KMS("picking CRTCs for %dx%d config\n", width, height);
-
-       drm_pick_crtcs(fb_helper, crtcs, modes, 0, width, height);
-
-       /* need to set the modesets up here for use later */
-       /* fill out the connector<->crtc mappings into the modesets */
-       for (i = 0; i < fb_helper->crtc_count; i++) {
-               modeset = &fb_helper->crtc_info[i].mode_set;
-               modeset->num_connectors = 0;
-       }
-
-       for (i = 0; i < fb_helper->connector_count; i++) {
-               struct drm_display_mode *mode = modes[i];
-               struct drm_fb_helper_crtc *fb_crtc = crtcs[i];
-               modeset = &fb_crtc->mode_set;
-
-               if (mode && fb_crtc) {
-                       DRM_DEBUG_KMS("desired mode %s set on crtc %d\n",
-                                     mode->name, fb_crtc->mode_set.crtc->base.id);
-                       fb_crtc->desired_mode = mode;
-                       if (modeset->mode)
-                               drm_mode_destroy(dev, modeset->mode);
-                       modeset->mode = drm_mode_duplicate(dev,
-                                                          fb_crtc->desired_mode);
-                       modeset->connectors[modeset->num_connectors++] = fb_helper->connector_info[i]->connector;
-               }
-       }
-
-       kfree(crtcs);
-       kfree(modes);
-       kfree(enabled);
-}
-
-/**
- * drm_helper_initial_config - setup a sane initial connector configuration
- * @dev: DRM device
- *
- * LOCKING:
- * Called at init time, must take mode config lock.
- *
- * Scan the CRTCs and connectors and try to put together an initial setup.
- * At the moment, this is a cloned configuration across all heads with
- * a new framebuffer object as the backing store.
- *
- * RETURNS:
- * Zero if everything went ok, nonzero otherwise.
- */
-bool drm_fb_helper_initial_config(struct drm_fb_helper *fb_helper, int bpp_sel)
-{
-       struct drm_device *dev = fb_helper->dev;
-       int count = 0;
-
-       /* disable all the possible outputs/crtcs before entering KMS mode */
-       drm_helper_disable_unused_functions(fb_helper->dev);
-
-       drm_fb_helper_parse_command_line(fb_helper);
-
-       count = drm_fb_helper_probe_connector_modes(fb_helper,
-                                                   dev->mode_config.max_width,
-                                                   dev->mode_config.max_height);
-       /*
-        * we shouldn't end up with no modes here.
-        */
-       if (count == 0) {
-               printk(KERN_INFO "No connectors reported connected with modes\n");
-       }
-       drm_setup_crtcs(fb_helper);
-
-       return drm_fb_helper_single_fb_probe(fb_helper, bpp_sel);
-}
-EXPORT_SYMBOL(drm_fb_helper_initial_config);
-
-bool drm_fb_helper_hotplug_event(struct drm_fb_helper *fb_helper)
-{
-       int count = 0;
-       u32 max_width, max_height, bpp_sel;
-       bool bound = false, crtcs_bound = false;
-       struct drm_crtc *crtc;
-
-       if (!fb_helper->fb)
-               return false;
-
-       list_for_each_entry(crtc, &fb_helper->dev->mode_config.crtc_list, head) {
-               if (crtc->fb)
-                       crtcs_bound = true;
-               if (crtc->fb == fb_helper->fb)
-                       bound = true;
-       }
-
-       if (!bound && crtcs_bound) {
-               fb_helper->delayed_hotplug = true;
-               return false;
-       }
-       DRM_DEBUG_KMS("\n");
-
-       max_width = fb_helper->fb->width;
-       max_height = fb_helper->fb->height;
-       bpp_sel = fb_helper->fb->bits_per_pixel;
-
-       count = drm_fb_helper_probe_connector_modes(fb_helper, max_width,
-                                                   max_height);
-       drm_setup_crtcs(fb_helper);
-
-       return drm_fb_helper_single_fb_probe(fb_helper, bpp_sel);
-}
-EXPORT_SYMBOL(drm_fb_helper_hotplug_event);
-
diff --git a/services4/3rdparty/linux_drm/drm_fops.c b/services4/3rdparty/linux_drm/drm_fops.c
deleted file mode 100644 (file)
index a39794b..0000000
+++ /dev/null
@@ -1,651 +0,0 @@
-/**
- * \file drm_fops.c
- * File operations for DRM
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Daryll Strauss <daryll@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Mon Jan  4 08:58:31 1999 by faith@valinux.com
- *
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-#include <linux/poll.h>
-#include <linux/slab.h>
-
-/* from BKL pushdown: note that nothing else serializes idr_find() */
-DEFINE_MUTEX(drm_global_mutex);
-EXPORT_SYMBOL(drm_global_mutex);
-
-static int drm_open_helper(struct inode *inode, struct file *filp,
-                          struct drm_device * dev);
-
-static int drm_setup(struct drm_device * dev)
-{
-       int i;
-       int ret;
-
-       if (dev->driver->firstopen) {
-               ret = dev->driver->firstopen(dev);
-               if (ret != 0)
-                       return ret;
-       }
-
-       atomic_set(&dev->ioctl_count, 0);
-       atomic_set(&dev->vma_count, 0);
-
-       if (drm_core_check_feature(dev, DRIVER_HAVE_DMA) &&
-           !drm_core_check_feature(dev, DRIVER_MODESET)) {
-               dev->buf_use = 0;
-               atomic_set(&dev->buf_alloc, 0);
-
-               i = drm_dma_setup(dev);
-               if (i < 0)
-                       return i;
-       }
-
-       for (i = 0; i < ARRAY_SIZE(dev->counts); i++)
-               atomic_set(&dev->counts[i], 0);
-
-       dev->sigdata.lock = NULL;
-
-       dev->queue_count = 0;
-       dev->queue_reserved = 0;
-       dev->queue_slots = 0;
-       dev->queuelist = NULL;
-       dev->context_flag = 0;
-       dev->interrupt_flag = 0;
-       dev->dma_flag = 0;
-       dev->last_context = 0;
-       dev->last_switch = 0;
-       dev->last_checked = 0;
-       init_waitqueue_head(&dev->context_wait);
-       dev->if_version = 0;
-
-       dev->ctx_start = 0;
-       dev->lck_start = 0;
-
-       dev->buf_async = NULL;
-       init_waitqueue_head(&dev->buf_readers);
-       init_waitqueue_head(&dev->buf_writers);
-
-       DRM_DEBUG("\n");
-
-       /*
-        * The kernel's context could be created here, but is now created
-        * in drm_dma_enqueue.  This is more resource-efficient for
-        * hardware that does not do DMA, but may mean that
-        * drm_select_queue fails between the time the interrupt is
-        * initialized and the time the queues are initialized.
-        */
-
-       return 0;
-}
-
-/**
- * Open file.
- *
- * \param inode device inode
- * \param filp file pointer.
- * \return zero on success or a negative number on failure.
- *
- * Searches the DRM device with the same minor number, calls open_helper(), and
- * increments the device open count. If the open count was previous at zero,
- * i.e., it's the first that the device is open, then calls setup().
- */
-int drm_open(struct inode *inode, struct file *filp)
-{
-       struct drm_device *dev = NULL;
-       int minor_id = iminor(inode);
-       struct drm_minor *minor;
-       int retcode = 0;
-
-       minor = idr_find(&drm_minors_idr, minor_id);
-       if (!minor)
-               return -ENODEV;
-
-       if (!(dev = minor->dev))
-               return -ENODEV;
-
-       retcode = drm_open_helper(inode, filp, dev);
-       if (!retcode) {
-               atomic_inc(&dev->counts[_DRM_STAT_OPENS]);
-               if (!dev->open_count++)
-                       retcode = drm_setup(dev);
-       }
-       if (!retcode) {
-               mutex_lock(&dev->struct_mutex);
-               if (minor->type == DRM_MINOR_LEGACY) {
-                       if (dev->dev_mapping == NULL)
-                               dev->dev_mapping = inode->i_mapping;
-                       else if (dev->dev_mapping != inode->i_mapping)
-                               retcode = -ENODEV;
-               }
-               mutex_unlock(&dev->struct_mutex);
-       }
-
-       return retcode;
-}
-EXPORT_SYMBOL(drm_open);
-
-/**
- * File \c open operation.
- *
- * \param inode device inode.
- * \param filp file pointer.
- *
- * Puts the dev->fops corresponding to the device minor number into
- * \p filp, call the \c open method, and restore the file operations.
- */
-int drm_stub_open(struct inode *inode, struct file *filp)
-{
-       struct drm_device *dev = NULL;
-       struct drm_minor *minor;
-       int minor_id = iminor(inode);
-       int err = -ENODEV;
-       const struct file_operations *old_fops;
-
-       DRM_DEBUG("\n");
-
-       mutex_lock(&drm_global_mutex);
-       minor = idr_find(&drm_minors_idr, minor_id);
-       if (!minor)
-               goto out;
-
-       if (!(dev = minor->dev))
-               goto out;
-
-       old_fops = filp->f_op;
-       filp->f_op = fops_get(&dev->driver->fops);
-       if (filp->f_op == NULL) {
-               filp->f_op = old_fops;
-               goto out;
-       }
-       if (filp->f_op->open && (err = filp->f_op->open(inode, filp))) {
-               fops_put(filp->f_op);
-               filp->f_op = fops_get(old_fops);
-       }
-       fops_put(old_fops);
-
-out:
-       mutex_unlock(&drm_global_mutex);
-       return err;
-}
-
-/**
- * Check whether DRI will run on this CPU.
- *
- * \return non-zero if the DRI will run on this CPU, or zero otherwise.
- */
-static int drm_cpu_valid(void)
-{
-#if defined(__i386__)
-       if (boot_cpu_data.x86 == 3)
-               return 0;       /* No cmpxchg on a 386 */
-#endif
-#if defined(__sparc__) && !defined(__sparc_v9__)
-       return 0;               /* No cmpxchg before v9 sparc. */
-#endif
-       return 1;
-}
-
-/**
- * Called whenever a process opens /dev/drm.
- *
- * \param inode device inode.
- * \param filp file pointer.
- * \param dev device.
- * \return zero on success or a negative number on failure.
- *
- * Creates and initializes a drm_file structure for the file private data in \p
- * filp and add it into the double linked list in \p dev.
- */
-static int drm_open_helper(struct inode *inode, struct file *filp,
-                          struct drm_device * dev)
-{
-       int minor_id = iminor(inode);
-       struct drm_file *priv;
-       int ret;
-
-       if (filp->f_flags & O_EXCL)
-               return -EBUSY;  /* No exclusive opens */
-       if (!drm_cpu_valid())
-               return -EINVAL;
-
-       DRM_DEBUG("pid = %d, minor = %d\n", task_pid_nr(current), minor_id);
-
-       priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-       if (!priv)
-               return -ENOMEM;
-
-       filp->private_data = priv;
-       priv->filp = filp;
-       priv->uid = current_euid();
-       priv->pid = task_pid_nr(current);
-       priv->minor = idr_find(&drm_minors_idr, minor_id);
-       priv->ioctl_count = 0;
-       /* for compatibility root is always authenticated */
-       priv->authenticated = capable(CAP_SYS_ADMIN);
-       priv->lock_count = 0;
-
-       INIT_LIST_HEAD(&priv->lhead);
-       INIT_LIST_HEAD(&priv->fbs);
-       INIT_LIST_HEAD(&priv->event_list);
-       init_waitqueue_head(&priv->event_wait);
-       priv->event_space = 4096; /* set aside 4k for event buffer */
-
-       if (dev->driver->driver_features & DRIVER_GEM)
-               drm_gem_open(dev, priv);
-
-       if (dev->driver->open) {
-               ret = dev->driver->open(dev, priv);
-               if (ret < 0)
-                       goto out_free;
-       }
-
-
-       /* if there is no current master make this fd it */
-       mutex_lock(&dev->struct_mutex);
-       if (!priv->minor->master) {
-               /* create a new master */
-               priv->minor->master = drm_master_create(priv->minor);
-               if (!priv->minor->master) {
-                       mutex_unlock(&dev->struct_mutex);
-                       ret = -ENOMEM;
-                       goto out_free;
-               }
-
-               priv->is_master = 1;
-               /* take another reference for the copy in the local file priv */
-               priv->master = drm_master_get(priv->minor->master);
-
-               priv->authenticated = 1;
-
-               mutex_unlock(&dev->struct_mutex);
-               if (dev->driver->master_create) {
-                       ret = dev->driver->master_create(dev, priv->master);
-                       if (ret) {
-                               mutex_lock(&dev->struct_mutex);
-                               /* drop both references if this fails */
-                               drm_master_put(&priv->minor->master);
-                               drm_master_put(&priv->master);
-                               mutex_unlock(&dev->struct_mutex);
-                               goto out_free;
-                       }
-               }
-               mutex_lock(&dev->struct_mutex);
-               if (dev->driver->master_set) {
-                       ret = dev->driver->master_set(dev, priv, true);
-                       if (ret) {
-                               /* drop both references if this fails */
-                               drm_master_put(&priv->minor->master);
-                               drm_master_put(&priv->master);
-                               mutex_unlock(&dev->struct_mutex);
-                               goto out_free;
-                       }
-               }
-               mutex_unlock(&dev->struct_mutex);
-       } else {
-               /* get a reference to the master */
-               priv->master = drm_master_get(priv->minor->master);
-               mutex_unlock(&dev->struct_mutex);
-       }
-
-       mutex_lock(&dev->struct_mutex);
-       list_add(&priv->lhead, &dev->filelist);
-       mutex_unlock(&dev->struct_mutex);
-
-#ifdef __alpha__
-       /*
-        * Default the hose
-        */
-       if (!dev->hose) {
-               struct pci_dev *pci_dev;
-               pci_dev = pci_get_class(PCI_CLASS_DISPLAY_VGA << 8, NULL);
-               if (pci_dev) {
-                       dev->hose = pci_dev->sysdata;
-                       pci_dev_put(pci_dev);
-               }
-               if (!dev->hose) {
-                       struct pci_bus *b = pci_bus_b(pci_root_buses.next);
-                       if (b)
-                               dev->hose = b->sysdata;
-               }
-       }
-#endif
-
-       return 0;
-      out_free:
-       kfree(priv);
-       filp->private_data = NULL;
-       return ret;
-}
-
-/** No-op. */
-int drm_fasync(int fd, struct file *filp, int on)
-{
-       struct drm_file *priv = filp->private_data;
-       struct drm_device *dev = priv->minor->dev;
-
-       DRM_DEBUG("fd = %d, device = 0x%lx\n", fd,
-                 (long)old_encode_dev(priv->minor->device));
-       return fasync_helper(fd, filp, on, &dev->buf_async);
-}
-EXPORT_SYMBOL(drm_fasync);
-
-/*
- * Reclaim locked buffers; note that this may be a bad idea if the current
- * context doesn't have the hw lock...
- */
-static void drm_reclaim_locked_buffers(struct drm_device *dev, struct file *f)
-{
-       struct drm_file *file_priv = f->private_data;
-
-       if (drm_i_have_hw_lock(dev, file_priv)) {
-               dev->driver->reclaim_buffers_locked(dev, file_priv);
-       } else {
-               unsigned long _end = jiffies + 3 * DRM_HZ;
-               int locked = 0;
-
-               drm_idlelock_take(&file_priv->master->lock);
-
-               /*
-                * Wait for a while.
-                */
-               do {
-                       spin_lock_bh(&file_priv->master->lock.spinlock);
-                       locked = file_priv->master->lock.idle_has_lock;
-                       spin_unlock_bh(&file_priv->master->lock.spinlock);
-                       if (locked)
-                               break;
-                       schedule();
-               } while (!time_after_eq(jiffies, _end));
-
-               if (!locked) {
-                       DRM_ERROR("reclaim_buffers_locked() deadlock. Please rework this\n"
-                                 "\tdriver to use reclaim_buffers_idlelocked() instead.\n"
-                                 "\tI will go on reclaiming the buffers anyway.\n");
-               }
-
-               dev->driver->reclaim_buffers_locked(dev, file_priv);
-               drm_idlelock_release(&file_priv->master->lock);
-       }
-}
-
-static void drm_master_release(struct drm_device *dev, struct file *filp)
-{
-       struct drm_file *file_priv = filp->private_data;
-
-       if (dev->driver->reclaim_buffers_locked &&
-           file_priv->master->lock.hw_lock)
-               drm_reclaim_locked_buffers(dev, filp);
-
-       if (dev->driver->reclaim_buffers_idlelocked &&
-           file_priv->master->lock.hw_lock) {
-               drm_idlelock_take(&file_priv->master->lock);
-               dev->driver->reclaim_buffers_idlelocked(dev, file_priv);
-               drm_idlelock_release(&file_priv->master->lock);
-       }
-
-
-       if (drm_i_have_hw_lock(dev, file_priv)) {
-               DRM_DEBUG("File %p released, freeing lock for context %d\n",
-                         filp, _DRM_LOCKING_CONTEXT(file_priv->master->lock.hw_lock->lock));
-               drm_lock_free(&file_priv->master->lock,
-                             _DRM_LOCKING_CONTEXT(file_priv->master->lock.hw_lock->lock));
-       }
-
-       if (drm_core_check_feature(dev, DRIVER_HAVE_DMA) &&
-           !dev->driver->reclaim_buffers_locked) {
-               dev->driver->reclaim_buffers(dev, file_priv);
-       }
-}
-
-static void drm_events_release(struct drm_file *file_priv)
-{
-       struct drm_device *dev = file_priv->minor->dev;
-       struct drm_pending_event *e, *et;
-       struct drm_pending_vblank_event *v, *vt;
-       unsigned long flags;
-
-       spin_lock_irqsave(&dev->event_lock, flags);
-
-       /* Remove pending flips */
-       list_for_each_entry_safe(v, vt, &dev->vblank_event_list, base.link)
-               if (v->base.file_priv == file_priv) {
-                       list_del(&v->base.link);
-                       drm_vblank_put(dev, v->pipe);
-                       v->base.destroy(&v->base);
-               }
-
-       /* Remove unconsumed events */
-       list_for_each_entry_safe(e, et, &file_priv->event_list, link)
-               e->destroy(e);
-
-       spin_unlock_irqrestore(&dev->event_lock, flags);
-}
-
-/**
- * Release file.
- *
- * \param inode device inode
- * \param file_priv DRM file private.
- * \return zero on success or a negative number on failure.
- *
- * If the hardware lock is held then free it, and take it again for the kernel
- * context since it's necessary to reclaim buffers. Unlink the file private
- * data from its list and free it. Decreases the open count and if it reaches
- * zero calls drm_lastclose().
- */
-int drm_release(struct inode *inode, struct file *filp)
-{
-       struct drm_file *file_priv = filp->private_data;
-       struct drm_device *dev = file_priv->minor->dev;
-       int retcode = 0;
-
-       mutex_lock(&drm_global_mutex);
-
-       DRM_DEBUG("open_count = %d\n", dev->open_count);
-
-       if (dev->driver->preclose)
-               dev->driver->preclose(dev, file_priv);
-
-       /* ========================================================
-        * Begin inline drm_release
-        */
-
-       DRM_DEBUG("pid = %d, device = 0x%lx, open_count = %d\n",
-                 task_pid_nr(current),
-                 (long)old_encode_dev(file_priv->minor->device),
-                 dev->open_count);
-
-       /* if the master has gone away we can't do anything with the lock */
-       if (file_priv->minor->master)
-               drm_master_release(dev, filp);
-
-       drm_events_release(file_priv);
-
-       if (dev->driver->driver_features & DRIVER_GEM)
-               drm_gem_release(dev, file_priv);
-
-       if (dev->driver->driver_features & DRIVER_MODESET)
-               drm_fb_release(file_priv);
-
-       mutex_lock(&dev->ctxlist_mutex);
-       if (!list_empty(&dev->ctxlist)) {
-               struct drm_ctx_list *pos, *n;
-
-               list_for_each_entry_safe(pos, n, &dev->ctxlist, head) {
-                       if (pos->tag == file_priv &&
-                           pos->handle != DRM_KERNEL_CONTEXT) {
-                               if (dev->driver->context_dtor)
-                                       dev->driver->context_dtor(dev,
-                                                                 pos->handle);
-
-                               drm_ctxbitmap_free(dev, pos->handle);
-
-                               list_del(&pos->head);
-                               kfree(pos);
-                               --dev->ctx_count;
-                       }
-               }
-       }
-       mutex_unlock(&dev->ctxlist_mutex);
-
-       mutex_lock(&dev->struct_mutex);
-
-       if (file_priv->is_master) {
-               struct drm_master *master = file_priv->master;
-               struct drm_file *temp;
-               list_for_each_entry(temp, &dev->filelist, lhead) {
-                       if ((temp->master == file_priv->master) &&
-                           (temp != file_priv))
-                               temp->authenticated = 0;
-               }
-
-               /**
-                * Since the master is disappearing, so is the
-                * possibility to lock.
-                */
-
-               if (master->lock.hw_lock) {
-                       if (dev->sigdata.lock == master->lock.hw_lock)
-                               dev->sigdata.lock = NULL;
-                       master->lock.hw_lock = NULL;
-                       master->lock.file_priv = NULL;
-                       wake_up_interruptible_all(&master->lock.lock_queue);
-               }
-
-               if (file_priv->minor->master == file_priv->master) {
-                       /* drop the reference held my the minor */
-                       if (dev->driver->master_drop)
-                               dev->driver->master_drop(dev, file_priv, true);
-                       drm_master_put(&file_priv->minor->master);
-               }
-       }
-
-       /* drop the reference held my the file priv */
-       drm_master_put(&file_priv->master);
-       file_priv->is_master = 0;
-       list_del(&file_priv->lhead);
-       mutex_unlock(&dev->struct_mutex);
-
-       if (dev->driver->postclose)
-               dev->driver->postclose(dev, file_priv);
-       kfree(file_priv);
-
-       /* ========================================================
-        * End inline drm_release
-        */
-
-       atomic_inc(&dev->counts[_DRM_STAT_CLOSES]);
-       if (!--dev->open_count) {
-               if (atomic_read(&dev->ioctl_count)) {
-                       DRM_ERROR("Device busy: %d\n",
-                                 atomic_read(&dev->ioctl_count));
-                       retcode = -EBUSY;
-               } else
-                       retcode = drm_lastclose(dev);
-       }
-       mutex_unlock(&drm_global_mutex);
-
-       return retcode;
-}
-EXPORT_SYMBOL(drm_release);
-
-static bool
-drm_dequeue_event(struct drm_file *file_priv,
-                 size_t total, size_t max, struct drm_pending_event **out)
-{
-       struct drm_device *dev = file_priv->minor->dev;
-       struct drm_pending_event *e;
-       unsigned long flags;
-       bool ret = false;
-
-       spin_lock_irqsave(&dev->event_lock, flags);
-
-       *out = NULL;
-       if (list_empty(&file_priv->event_list))
-               goto out;
-       e = list_first_entry(&file_priv->event_list,
-                            struct drm_pending_event, link);
-       if (e->event->length + total > max)
-               goto out;
-
-       file_priv->event_space += e->event->length;
-       list_del(&e->link);
-       *out = e;
-       ret = true;
-
-out:
-       spin_unlock_irqrestore(&dev->event_lock, flags);
-       return ret;
-}
-
-ssize_t drm_read(struct file *filp, char __user *buffer,
-                size_t count, loff_t *offset)
-{
-       struct drm_file *file_priv = filp->private_data;
-       struct drm_pending_event *e;
-       size_t total;
-       ssize_t ret;
-
-       ret = wait_event_interruptible(file_priv->event_wait,
-                                      !list_empty(&file_priv->event_list));
-       if (ret < 0)
-               return ret;
-
-       total = 0;
-       while (drm_dequeue_event(file_priv, total, count, &e)) {
-               if (copy_to_user(buffer + total,
-                                e->event, e->event->length)) {
-                       total = -EFAULT;
-                       break;
-               }
-
-               total += e->event->length;
-               e->destroy(e);
-       }
-
-       return total;
-}
-EXPORT_SYMBOL(drm_read);
-
-unsigned int drm_poll(struct file *filp, struct poll_table_struct *wait)
-{
-       struct drm_file *file_priv = filp->private_data;
-       unsigned int mask = 0;
-
-       poll_wait(filp, &file_priv->event_wait, wait);
-
-       if (!list_empty(&file_priv->event_list))
-               mask |= POLLIN | POLLRDNORM;
-
-       return mask;
-}
-EXPORT_SYMBOL(drm_poll);
diff --git a/services4/3rdparty/linux_drm/drm_gem.c b/services4/3rdparty/linux_drm/drm_gem.c
deleted file mode 100644 (file)
index ea1c4b0..0000000
+++ /dev/null
@@ -1,581 +0,0 @@
-/*
- * Copyright Â© 2008 Intel Corporation
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
- * IN THE SOFTWARE.
- *
- * Authors:
- *    Eric Anholt <eric@anholt.net>
- *
- */
-
-#include <linux/types.h>
-#include <linux/slab.h>
-#include <linux/mm.h>
-#include <linux/uaccess.h>
-#include <linux/fs.h>
-#include <linux/file.h>
-#include <linux/module.h>
-#include <linux/mman.h>
-#include <linux/pagemap.h>
-#include "drmP.h"
-
-/** @file drm_gem.c
- *
- * This file provides some of the base ioctls and library routines for
- * the graphics memory manager implemented by each device driver.
- *
- * Because various devices have different requirements in terms of
- * synchronization and migration strategies, implementing that is left up to
- * the driver, and all that the general API provides should be generic --
- * allocating objects, reading/writing data with the cpu, freeing objects.
- * Even there, platform-dependent optimizations for reading/writing data with
- * the CPU mean we'll likely hook those out to driver-specific calls.  However,
- * the DRI2 implementation wants to have at least allocate/mmap be generic.
- *
- * The goal was to have swap-backed object allocation managed through
- * struct file.  However, file descriptors as handles to a struct file have
- * two major failings:
- * - Process limits prevent more than 1024 or so being used at a time by
- *   default.
- * - Inability to allocate high fds will aggravate the X Server's select()
- *   handling, and likely that of many GL client applications as well.
- *
- * This led to a plan of using our own integer IDs (called handles, following
- * DRM terminology) to mimic fds, and implement the fd syscalls we need as
- * ioctls.  The objects themselves will still include the struct file so
- * that we can transition to fds if the required kernel infrastructure shows
- * up at a later date, and as our interface with shmfs for memory allocation.
- */
-
-/*
- * We make up offsets for buffer objects so we can recognize them at
- * mmap time.
- */
-
-/* pgoff in mmap is an unsigned long, so we need to make sure that
- * the faked up offset will fit
- */
-
-#if BITS_PER_LONG == 64
-#define DRM_FILE_PAGE_OFFSET_START ((0xFFFFFFFFUL >> PAGE_SHIFT) + 1)
-#define DRM_FILE_PAGE_OFFSET_SIZE ((0xFFFFFFFFUL >> PAGE_SHIFT) * 16)
-#else
-#define DRM_FILE_PAGE_OFFSET_START ((0xFFFFFFFUL >> PAGE_SHIFT) + 1)
-#define DRM_FILE_PAGE_OFFSET_SIZE ((0xFFFFFFFUL >> PAGE_SHIFT) * 16)
-#endif
-
-/**
- * Initialize the GEM device fields
- */
-
-int
-drm_gem_init(struct drm_device *dev)
-{
-       struct drm_gem_mm *mm;
-
-       spin_lock_init(&dev->object_name_lock);
-       idr_init(&dev->object_name_idr);
-
-       mm = kzalloc(sizeof(struct drm_gem_mm), GFP_KERNEL);
-       if (!mm) {
-               DRM_ERROR("out of memory\n");
-               return -ENOMEM;
-       }
-
-       dev->mm_private = mm;
-
-       if (drm_ht_create(&mm->offset_hash, 19)) {
-               kfree(mm);
-               return -ENOMEM;
-       }
-
-       if (drm_mm_init(&mm->offset_manager, DRM_FILE_PAGE_OFFSET_START,
-                       DRM_FILE_PAGE_OFFSET_SIZE)) {
-               drm_ht_remove(&mm->offset_hash);
-               kfree(mm);
-               return -ENOMEM;
-       }
-
-       return 0;
-}
-
-void
-drm_gem_destroy(struct drm_device *dev)
-{
-       struct drm_gem_mm *mm = dev->mm_private;
-
-       drm_mm_takedown(&mm->offset_manager);
-       drm_ht_remove(&mm->offset_hash);
-       kfree(mm);
-       dev->mm_private = NULL;
-}
-
-/**
- * Initialize an already allocate GEM object of the specified size with
- * shmfs backing store.
- */
-int drm_gem_object_init(struct drm_device *dev,
-                       struct drm_gem_object *obj, size_t size)
-{
-       BUG_ON((size & (PAGE_SIZE - 1)) != 0);
-
-       obj->dev = dev;
-       obj->filp = shmem_file_setup("drm mm object", size, VM_NORESERVE);
-       if (IS_ERR(obj->filp))
-               return -ENOMEM;
-
-       kref_init(&obj->refcount);
-       atomic_set(&obj->handle_count, 0);
-       obj->size = size;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_gem_object_init);
-
-/**
- * Allocate a GEM object of the specified size with shmfs backing store
- */
-struct drm_gem_object *
-drm_gem_object_alloc(struct drm_device *dev, size_t size)
-{
-       struct drm_gem_object *obj;
-
-       obj = kzalloc(sizeof(*obj), GFP_KERNEL);
-       if (!obj)
-               goto free;
-
-       if (drm_gem_object_init(dev, obj, size) != 0)
-               goto free;
-
-       if (dev->driver->gem_init_object != NULL &&
-           dev->driver->gem_init_object(obj) != 0) {
-               goto fput;
-       }
-       return obj;
-fput:
-       /* Object_init mangles the global counters - readjust them. */
-       fput(obj->filp);
-free:
-       kfree(obj);
-       return NULL;
-}
-EXPORT_SYMBOL(drm_gem_object_alloc);
-
-/**
- * Removes the mapping from handle to filp for this object.
- */
-static int
-drm_gem_handle_delete(struct drm_file *filp, u32 handle)
-{
-       struct drm_device *dev;
-       struct drm_gem_object *obj;
-
-       /* This is gross. The idr system doesn't let us try a delete and
-        * return an error code.  It just spews if you fail at deleting.
-        * So, we have to grab a lock around finding the object and then
-        * doing the delete on it and dropping the refcount, or the user
-        * could race us to double-decrement the refcount and cause a
-        * use-after-free later.  Given the frequency of our handle lookups,
-        * we may want to use ida for number allocation and a hash table
-        * for the pointers, anyway.
-        */
-       spin_lock(&filp->table_lock);
-
-       /* Check if we currently have a reference on the object */
-       obj = idr_find(&filp->object_idr, handle);
-       if (obj == NULL) {
-               spin_unlock(&filp->table_lock);
-               return -EINVAL;
-       }
-       dev = obj->dev;
-
-       /* Release reference and decrement refcount. */
-       idr_remove(&filp->object_idr, handle);
-       spin_unlock(&filp->table_lock);
-
-       drm_gem_object_handle_unreference_unlocked(obj);
-
-       return 0;
-}
-
-/**
- * Create a handle for this object. This adds a handle reference
- * to the object, which includes a regular reference count. Callers
- * will likely want to dereference the object afterwards.
- */
-int
-drm_gem_handle_create(struct drm_file *file_priv,
-                      struct drm_gem_object *obj,
-                      u32 *handlep)
-{
-       int     ret;
-
-       /*
-        * Get the user-visible handle using idr.
-        */
-again:
-       /* ensure there is space available to allocate a handle */
-       if (idr_pre_get(&file_priv->object_idr, GFP_KERNEL) == 0)
-               return -ENOMEM;
-
-       /* do the allocation under our spinlock */
-       spin_lock(&file_priv->table_lock);
-       ret = idr_get_new_above(&file_priv->object_idr, obj, 1, (int *)handlep);
-       spin_unlock(&file_priv->table_lock);
-       if (ret == -EAGAIN)
-               goto again;
-
-       if (ret != 0)
-               return ret;
-
-       drm_gem_object_handle_reference(obj);
-       return 0;
-}
-EXPORT_SYMBOL(drm_gem_handle_create);
-
-/** Returns a reference to the object named by the handle. */
-struct drm_gem_object *
-drm_gem_object_lookup(struct drm_device *dev, struct drm_file *filp,
-                     u32 handle)
-{
-       struct drm_gem_object *obj;
-
-       spin_lock(&filp->table_lock);
-
-       /* Check if we currently have a reference on the object */
-       obj = idr_find(&filp->object_idr, handle);
-       if (obj == NULL) {
-               spin_unlock(&filp->table_lock);
-               return NULL;
-       }
-
-       drm_gem_object_reference(obj);
-
-       spin_unlock(&filp->table_lock);
-
-       return obj;
-}
-EXPORT_SYMBOL(drm_gem_object_lookup);
-
-/**
- * Releases the handle to an mm object.
- */
-int
-drm_gem_close_ioctl(struct drm_device *dev, void *data,
-                   struct drm_file *file_priv)
-{
-       struct drm_gem_close *args = data;
-       int ret;
-
-       if (!(dev->driver->driver_features & DRIVER_GEM))
-               return -ENODEV;
-
-       ret = drm_gem_handle_delete(file_priv, args->handle);
-
-       return ret;
-}
-
-/**
- * Create a global name for an object, returning the name.
- *
- * Note that the name does not hold a reference; when the object
- * is freed, the name goes away.
- */
-int
-drm_gem_flink_ioctl(struct drm_device *dev, void *data,
-                   struct drm_file *file_priv)
-{
-       struct drm_gem_flink *args = data;
-       struct drm_gem_object *obj;
-       int ret;
-
-       if (!(dev->driver->driver_features & DRIVER_GEM))
-               return -ENODEV;
-
-       obj = drm_gem_object_lookup(dev, file_priv, args->handle);
-       if (obj == NULL)
-               return -ENOENT;
-
-again:
-       if (idr_pre_get(&dev->object_name_idr, GFP_KERNEL) == 0) {
-               ret = -ENOMEM;
-               goto err;
-       }
-
-       spin_lock(&dev->object_name_lock);
-       if (!obj->name) {
-               ret = idr_get_new_above(&dev->object_name_idr, obj, 1,
-                                       &obj->name);
-               args->name = (uint64_t) obj->name;
-               spin_unlock(&dev->object_name_lock);
-
-               if (ret == -EAGAIN)
-                       goto again;
-
-               if (ret != 0)
-                       goto err;
-
-               /* Allocate a reference for the name table.  */
-               drm_gem_object_reference(obj);
-       } else {
-               args->name = (uint64_t) obj->name;
-               spin_unlock(&dev->object_name_lock);
-               ret = 0;
-       }
-
-err:
-       drm_gem_object_unreference_unlocked(obj);
-       return ret;
-}
-
-/**
- * Open an object using the global name, returning a handle and the size.
- *
- * This handle (of course) holds a reference to the object, so the object
- * will not go away until the handle is deleted.
- */
-int
-drm_gem_open_ioctl(struct drm_device *dev, void *data,
-                  struct drm_file *file_priv)
-{
-       struct drm_gem_open *args = data;
-       struct drm_gem_object *obj;
-       int ret;
-       u32 handle;
-
-       if (!(dev->driver->driver_features & DRIVER_GEM))
-               return -ENODEV;
-
-       spin_lock(&dev->object_name_lock);
-       obj = idr_find(&dev->object_name_idr, (int) args->name);
-       if (obj)
-               drm_gem_object_reference(obj);
-       spin_unlock(&dev->object_name_lock);
-       if (!obj)
-               return -ENOENT;
-
-       ret = drm_gem_handle_create(file_priv, obj, &handle);
-       drm_gem_object_unreference_unlocked(obj);
-       if (ret)
-               return ret;
-
-       args->handle = handle;
-       args->size = obj->size;
-
-       return 0;
-}
-
-/**
- * Called at device open time, sets up the structure for handling refcounting
- * of mm objects.
- */
-void
-drm_gem_open(struct drm_device *dev, struct drm_file *file_private)
-{
-       idr_init(&file_private->object_idr);
-       spin_lock_init(&file_private->table_lock);
-}
-
-/**
- * Called at device close to release the file's
- * handle references on objects.
- */
-static int
-drm_gem_object_release_handle(int id, void *ptr, void *data)
-{
-       struct drm_gem_object *obj = ptr;
-
-       drm_gem_object_handle_unreference_unlocked(obj);
-
-       return 0;
-}
-
-/**
- * Called at close time when the filp is going away.
- *
- * Releases any remaining references on objects by this filp.
- */
-void
-drm_gem_release(struct drm_device *dev, struct drm_file *file_private)
-{
-       idr_for_each(&file_private->object_idr,
-                    &drm_gem_object_release_handle, NULL);
-
-       idr_remove_all(&file_private->object_idr);
-       idr_destroy(&file_private->object_idr);
-}
-
-void
-drm_gem_object_release(struct drm_gem_object *obj)
-{
-       fput(obj->filp);
-}
-EXPORT_SYMBOL(drm_gem_object_release);
-
-/**
- * Called after the last reference to the object has been lost.
- * Must be called holding struct_ mutex
- *
- * Frees the object
- */
-void
-drm_gem_object_free(struct kref *kref)
-{
-       struct drm_gem_object *obj = (struct drm_gem_object *) kref;
-       struct drm_device *dev = obj->dev;
-
-       BUG_ON(!mutex_is_locked(&dev->struct_mutex));
-
-       if (dev->driver->gem_free_object != NULL)
-               dev->driver->gem_free_object(obj);
-}
-EXPORT_SYMBOL(drm_gem_object_free);
-
-static void drm_gem_object_ref_bug(struct kref *list_kref)
-{
-       BUG();
-}
-
-/**
- * Called after the last handle to the object has been closed
- *
- * Removes any name for the object. Note that this must be
- * called before drm_gem_object_free or we'll be touching
- * freed memory
- */
-void drm_gem_object_handle_free(struct drm_gem_object *obj)
-{
-       struct drm_device *dev = obj->dev;
-
-       /* Remove any name for this object */
-       spin_lock(&dev->object_name_lock);
-       if (obj->name) {
-               idr_remove(&dev->object_name_idr, obj->name);
-               obj->name = 0;
-               spin_unlock(&dev->object_name_lock);
-               /*
-                * The object name held a reference to this object, drop
-                * that now.
-               *
-               * This cannot be the last reference, since the handle holds one too.
-                */
-               kref_put(&obj->refcount, drm_gem_object_ref_bug);
-       } else
-               spin_unlock(&dev->object_name_lock);
-
-}
-EXPORT_SYMBOL(drm_gem_object_handle_free);
-
-void drm_gem_vm_open(struct vm_area_struct *vma)
-{
-       struct drm_gem_object *obj = vma->vm_private_data;
-
-       drm_gem_object_reference(obj);
-
-       mutex_lock(&obj->dev->struct_mutex);
-       drm_vm_open_locked(vma);
-       mutex_unlock(&obj->dev->struct_mutex);
-}
-EXPORT_SYMBOL(drm_gem_vm_open);
-
-void drm_gem_vm_close(struct vm_area_struct *vma)
-{
-       struct drm_gem_object *obj = vma->vm_private_data;
-
-       mutex_lock(&obj->dev->struct_mutex);
-       drm_vm_close_locked(vma);
-       drm_gem_object_unreference(obj);
-       mutex_unlock(&obj->dev->struct_mutex);
-}
-EXPORT_SYMBOL(drm_gem_vm_close);
-
-
-/**
- * drm_gem_mmap - memory map routine for GEM objects
- * @filp: DRM file pointer
- * @vma: VMA for the area to be mapped
- *
- * If a driver supports GEM object mapping, mmap calls on the DRM file
- * descriptor will end up here.
- *
- * If we find the object based on the offset passed in (vma->vm_pgoff will
- * contain the fake offset we created when the GTT map ioctl was called on
- * the object), we set up the driver fault handler so that any accesses
- * to the object can be trapped, to perform migration, GTT binding, surface
- * register allocation, or performance monitoring.
- */
-int drm_gem_mmap(struct file *filp, struct vm_area_struct *vma)
-{
-       struct drm_file *priv = filp->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_gem_mm *mm = dev->mm_private;
-       struct drm_local_map *map = NULL;
-       struct drm_gem_object *obj;
-       struct drm_hash_item *hash;
-       int ret = 0;
-
-       mutex_lock(&dev->struct_mutex);
-
-       if (drm_ht_find_item(&mm->offset_hash, vma->vm_pgoff, &hash)) {
-               mutex_unlock(&dev->struct_mutex);
-               return drm_mmap(filp, vma);
-       }
-
-       map = drm_hash_entry(hash, struct drm_map_list, hash)->map;
-       if (!map ||
-           ((map->flags & _DRM_RESTRICTED) && !capable(CAP_SYS_ADMIN))) {
-               ret =  -EPERM;
-               goto out_unlock;
-       }
-
-       /* Check for valid size. */
-       if (map->size < vma->vm_end - vma->vm_start) {
-               ret = -EINVAL;
-               goto out_unlock;
-       }
-
-       obj = map->handle;
-       if (!obj->dev->driver->gem_vm_ops) {
-               ret = -EINVAL;
-               goto out_unlock;
-       }
-
-       vma->vm_flags |= VM_RESERVED | VM_IO | VM_PFNMAP | VM_DONTEXPAND;
-       vma->vm_ops = obj->dev->driver->gem_vm_ops;
-       vma->vm_private_data = map->handle;
-       vma->vm_page_prot =  pgprot_writecombine(vm_get_page_prot(vma->vm_flags));
-
-       /* Take a ref for this mapping of the object, so that the fault
-        * handler can dereference the mmap offset's pointer to the object.
-        * This reference is cleaned up by the corresponding vm_close
-        * (which should happen whether the vma was created by this call, or
-        * by a vm_open due to mremap or partial unmap or whatever).
-        */
-       drm_gem_object_reference(obj);
-
-       vma->vm_file = filp;    /* Needed for drm_vm_open() */
-       drm_vm_open_locked(vma);
-
-out_unlock:
-       mutex_unlock(&dev->struct_mutex);
-
-       return ret;
-}
-EXPORT_SYMBOL(drm_gem_mmap);
diff --git a/services4/3rdparty/linux_drm/drm_global.c b/services4/3rdparty/linux_drm/drm_global.c
deleted file mode 100644 (file)
index c87dc96..0000000
+++ /dev/null
@@ -1,112 +0,0 @@
-/**************************************************************************
- *
- * Copyright 2008-2009 VMware, Inc., Palo Alto, CA., USA
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sub license, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice (including the
- * next paragraph) shall be included in all copies or substantial portions
- * of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
- * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
- * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
- * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
- * USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- **************************************************************************/
-/*
- * Authors: Thomas Hellstrom <thellstrom-at-vmware-dot-com>
- */
-
-#include <linux/mutex.h>
-#include <linux/slab.h>
-#include <linux/module.h>
-#include "drm_global.h"
-
-struct drm_global_item {
-       struct mutex mutex;
-       void *object;
-       int refcount;
-};
-
-static struct drm_global_item glob[DRM_GLOBAL_NUM];
-
-void drm_global_init(void)
-{
-       int i;
-
-       for (i = 0; i < DRM_GLOBAL_NUM; ++i) {
-               struct drm_global_item *item = &glob[i];
-               mutex_init(&item->mutex);
-               item->object = NULL;
-               item->refcount = 0;
-       }
-}
-
-void drm_global_release(void)
-{
-       int i;
-       for (i = 0; i < DRM_GLOBAL_NUM; ++i) {
-               struct drm_global_item *item = &glob[i];
-               BUG_ON(item->object != NULL);
-               BUG_ON(item->refcount != 0);
-       }
-}
-
-int drm_global_item_ref(struct drm_global_reference *ref)
-{
-       int ret;
-       struct drm_global_item *item = &glob[ref->global_type];
-       void *object;
-
-       mutex_lock(&item->mutex);
-       if (item->refcount == 0) {
-               item->object = kzalloc(ref->size, GFP_KERNEL);
-               if (unlikely(item->object == NULL)) {
-                       ret = -ENOMEM;
-                       goto out_err;
-               }
-
-               ref->object = item->object;
-               ret = ref->init(ref);
-               if (unlikely(ret != 0))
-                       goto out_err;
-
-       }
-       ++item->refcount;
-       ref->object = item->object;
-       object = item->object;
-       mutex_unlock(&item->mutex);
-       return 0;
-out_err:
-       mutex_unlock(&item->mutex);
-       item->object = NULL;
-       return ret;
-}
-EXPORT_SYMBOL(drm_global_item_ref);
-
-void drm_global_item_unref(struct drm_global_reference *ref)
-{
-       struct drm_global_item *item = &glob[ref->global_type];
-
-       mutex_lock(&item->mutex);
-       BUG_ON(item->refcount == 0);
-       BUG_ON(ref->object != item->object);
-       if (--item->refcount == 0) {
-               ref->release(ref);
-               item->object = NULL;
-       }
-       mutex_unlock(&item->mutex);
-}
-EXPORT_SYMBOL(drm_global_item_unref);
-
diff --git a/services4/3rdparty/linux_drm/drm_hashtab.c b/services4/3rdparty/linux_drm/drm_hashtab.c
deleted file mode 100644 (file)
index a93d7b4..0000000
+++ /dev/null
@@ -1,207 +0,0 @@
-/**************************************************************************
- *
- * Copyright 2006 Tungsten Graphics, Inc., Bismarck, ND. USA.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sub license, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice (including the
- * next paragraph) shall be included in all copies or substantial portions
- * of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
- * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
- * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
- * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
- * USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- *
- **************************************************************************/
-/*
- * Simple open hash tab implementation.
- *
- * Authors:
- * Thomas Hellström <thomas-at-tungstengraphics-dot-com>
- */
-
-#include "drmP.h"
-#include "drm_hashtab.h"
-#include <linux/hash.h>
-#include <linux/slab.h>
-
-int drm_ht_create(struct drm_open_hash *ht, unsigned int order)
-{
-       unsigned int i;
-
-       ht->size = 1 << order;
-       ht->order = order;
-       ht->fill = 0;
-       ht->table = NULL;
-       ht->use_vmalloc = ((ht->size * sizeof(*ht->table)) > PAGE_SIZE);
-       if (!ht->use_vmalloc) {
-               ht->table = kcalloc(ht->size, sizeof(*ht->table), GFP_KERNEL);
-       }
-       if (!ht->table) {
-               ht->use_vmalloc = 1;
-               ht->table = vmalloc(ht->size*sizeof(*ht->table));
-       }
-       if (!ht->table) {
-               DRM_ERROR("Out of memory for hash table\n");
-               return -ENOMEM;
-       }
-       for (i=0; i< ht->size; ++i) {
-               INIT_HLIST_HEAD(&ht->table[i]);
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_ht_create);
-
-void drm_ht_verbose_list(struct drm_open_hash *ht, unsigned long key)
-{
-       struct drm_hash_item *entry;
-       struct hlist_head *h_list;
-       struct hlist_node *list;
-       unsigned int hashed_key;
-       int count = 0;
-
-       hashed_key = hash_long(key, ht->order);
-       DRM_DEBUG("Key is 0x%08lx, Hashed key is 0x%08x\n", key, hashed_key);
-       h_list = &ht->table[hashed_key];
-       hlist_for_each(list, h_list) {
-               entry = hlist_entry(list, struct drm_hash_item, head);
-               DRM_DEBUG("count %d, key: 0x%08lx\n", count++, entry->key);
-       }
-}
-
-static struct hlist_node *drm_ht_find_key(struct drm_open_hash *ht,
-                                         unsigned long key)
-{
-       struct drm_hash_item *entry;
-       struct hlist_head *h_list;
-       struct hlist_node *list;
-       unsigned int hashed_key;
-
-       hashed_key = hash_long(key, ht->order);
-       h_list = &ht->table[hashed_key];
-       hlist_for_each(list, h_list) {
-               entry = hlist_entry(list, struct drm_hash_item, head);
-               if (entry->key == key)
-                       return list;
-               if (entry->key > key)
-                       break;
-       }
-       return NULL;
-}
-
-
-int drm_ht_insert_item(struct drm_open_hash *ht, struct drm_hash_item *item)
-{
-       struct drm_hash_item *entry;
-       struct hlist_head *h_list;
-       struct hlist_node *list, *parent;
-       unsigned int hashed_key;
-       unsigned long key = item->key;
-
-       hashed_key = hash_long(key, ht->order);
-       h_list = &ht->table[hashed_key];
-       parent = NULL;
-       hlist_for_each(list, h_list) {
-               entry = hlist_entry(list, struct drm_hash_item, head);
-               if (entry->key == key)
-                       return -EINVAL;
-               if (entry->key > key)
-                       break;
-               parent = list;
-       }
-       if (parent) {
-               hlist_add_after(parent, &item->head);
-       } else {
-               hlist_add_head(&item->head, h_list);
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_ht_insert_item);
-
-/*
- * Just insert an item and return any "bits" bit key that hasn't been
- * used before.
- */
-int drm_ht_just_insert_please(struct drm_open_hash *ht, struct drm_hash_item *item,
-                             unsigned long seed, int bits, int shift,
-                             unsigned long add)
-{
-       int ret;
-       unsigned long mask = (1 << bits) - 1;
-       unsigned long first, unshifted_key;
-
-       unshifted_key = hash_long(seed, bits);
-       first = unshifted_key;
-       do {
-               item->key = (unshifted_key << shift) + add;
-               ret = drm_ht_insert_item(ht, item);
-               if (ret)
-                       unshifted_key = (unshifted_key + 1) & mask;
-       } while(ret && (unshifted_key != first));
-
-       if (ret) {
-               DRM_ERROR("Available key bit space exhausted\n");
-               return -EINVAL;
-       }
-       return 0;
-}
-EXPORT_SYMBOL(drm_ht_just_insert_please);
-
-int drm_ht_find_item(struct drm_open_hash *ht, unsigned long key,
-                    struct drm_hash_item **item)
-{
-       struct hlist_node *list;
-
-       list = drm_ht_find_key(ht, key);
-       if (!list)
-               return -EINVAL;
-
-       *item = hlist_entry(list, struct drm_hash_item, head);
-       return 0;
-}
-EXPORT_SYMBOL(drm_ht_find_item);
-
-int drm_ht_remove_key(struct drm_open_hash *ht, unsigned long key)
-{
-       struct hlist_node *list;
-
-       list = drm_ht_find_key(ht, key);
-       if (list) {
-               hlist_del_init(list);
-               ht->fill--;
-               return 0;
-       }
-       return -EINVAL;
-}
-
-int drm_ht_remove_item(struct drm_open_hash *ht, struct drm_hash_item *item)
-{
-       hlist_del_init(&item->head);
-       ht->fill--;
-       return 0;
-}
-EXPORT_SYMBOL(drm_ht_remove_item);
-
-void drm_ht_remove(struct drm_open_hash *ht)
-{
-       if (ht->table) {
-               if (ht->use_vmalloc)
-                       vfree(ht->table);
-               else
-                       kfree(ht->table);
-               ht->table = NULL;
-       }
-}
-EXPORT_SYMBOL(drm_ht_remove);
diff --git a/services4/3rdparty/linux_drm/drm_info.c b/services4/3rdparty/linux_drm/drm_info.c
deleted file mode 100644 (file)
index 3cdbaf3..0000000
+++ /dev/null
@@ -1,325 +0,0 @@
-/**
- * \file drm_info.c
- * DRM info file implementations
- *
- * \author Ben Gamari <bgamari@gmail.com>
- */
-
-/*
- * Created: Sun Dec 21 13:09:50 2008 by bgamari@gmail.com
- *
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * Copyright 2008 Ben Gamari <bgamari@gmail.com>
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/seq_file.h>
-#include "drmP.h"
-
-/**
- * Called when "/proc/dri/.../name" is read.
- *
- * Prints the device name together with the bus id if available.
- */
-int drm_name_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_minor *minor = node->minor;
-       struct drm_device *dev = minor->dev;
-       struct drm_master *master = minor->master;
-
-       if (!master)
-               return 0;
-
-       if (drm_core_check_feature(dev, DRIVER_USE_PLATFORM_DEVICE)) {
-               if (master->unique) {
-                       seq_printf(m, "%s %s %s\n",
-                                       dev->driver->platform_device->name,
-                                       dev_name(dev->dev), master->unique);
-               } else {
-                       seq_printf(m, "%s\n",
-                               dev->driver->platform_device->name);
-               }
-       } else {
-               if (master->unique) {
-                       seq_printf(m, "%s %s %s\n",
-                               dev->driver->pci_driver.name,
-                               dev_name(dev->dev), master->unique);
-               } else {
-                       seq_printf(m, "%s %s\n", dev->driver->pci_driver.name,
-                               dev_name(dev->dev));
-               }
-       }
-
-       return 0;
-}
-
-/**
- * Called when "/proc/dri/.../vm" is read.
- *
- * Prints information about all mappings in drm_device::maplist.
- */
-int drm_vm_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_device *dev = node->minor->dev;
-       struct drm_local_map *map;
-       struct drm_map_list *r_list;
-
-       /* Hardcoded from _DRM_FRAME_BUFFER,
-          _DRM_REGISTERS, _DRM_SHM, _DRM_AGP, and
-          _DRM_SCATTER_GATHER and _DRM_CONSISTENT */
-       const char *types[] = { "FB", "REG", "SHM", "AGP", "SG", "PCI" };
-       const char *type;
-       int i;
-
-       mutex_lock(&dev->struct_mutex);
-       seq_printf(m, "slot      offset       size type flags    address mtrr\n\n");
-       i = 0;
-       list_for_each_entry(r_list, &dev->maplist, head) {
-               map = r_list->map;
-               if (!map)
-                       continue;
-               if (map->type < 0 || map->type > 5)
-                       type = "??";
-               else
-                       type = types[map->type];
-
-               seq_printf(m, "%4d 0x%016llx 0x%08lx %4.4s  0x%02x 0x%08lx ",
-                          i,
-                          (unsigned long long)map->offset,
-                          map->size, type, map->flags,
-                          (unsigned long) r_list->user_token);
-               if (map->mtrr < 0)
-                       seq_printf(m, "none\n");
-               else
-                       seq_printf(m, "%4d\n", map->mtrr);
-               i++;
-       }
-       mutex_unlock(&dev->struct_mutex);
-       return 0;
-}
-
-/**
- * Called when "/proc/dri/.../queues" is read.
- */
-int drm_queues_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_device *dev = node->minor->dev;
-       int i;
-       struct drm_queue *q;
-
-       mutex_lock(&dev->struct_mutex);
-       seq_printf(m, "  ctx/flags   use   fin"
-                  "   blk/rw/rwf  wait    flushed         queued"
-                  "      locks\n\n");
-       for (i = 0; i < dev->queue_count; i++) {
-               q = dev->queuelist[i];
-               atomic_inc(&q->use_count);
-               seq_printf(m,   "%5d/0x%03x %5d %5d"
-                          " %5d/%c%c/%c%c%c %5Zd\n",
-                          i,
-                          q->flags,
-                          atomic_read(&q->use_count),
-                          atomic_read(&q->finalization),
-                          atomic_read(&q->block_count),
-                          atomic_read(&q->block_read) ? 'r' : '-',
-                          atomic_read(&q->block_write) ? 'w' : '-',
-                          waitqueue_active(&q->read_queue) ? 'r' : '-',
-                          waitqueue_active(&q->write_queue) ? 'w' : '-',
-                          waitqueue_active(&q->flush_queue) ? 'f' : '-',
-                          DRM_BUFCOUNT(&q->waitlist));
-               atomic_dec(&q->use_count);
-       }
-       mutex_unlock(&dev->struct_mutex);
-       return 0;
-}
-
-/**
- * Called when "/proc/dri/.../bufs" is read.
- */
-int drm_bufs_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_device *dev = node->minor->dev;
-       struct drm_device_dma *dma;
-       int i, seg_pages;
-
-       mutex_lock(&dev->struct_mutex);
-       dma = dev->dma;
-       if (!dma) {
-               mutex_unlock(&dev->struct_mutex);
-               return 0;
-       }
-
-       seq_printf(m, " o     size count  free   segs pages    kB\n\n");
-       for (i = 0; i <= DRM_MAX_ORDER; i++) {
-               if (dma->bufs[i].buf_count) {
-                       seg_pages = dma->bufs[i].seg_count * (1 << dma->bufs[i].page_order);
-                       seq_printf(m, "%2d %8d %5d %5d %5d %5d %5ld\n",
-                                  i,
-                                  dma->bufs[i].buf_size,
-                                  dma->bufs[i].buf_count,
-                                  atomic_read(&dma->bufs[i].freelist.count),
-                                  dma->bufs[i].seg_count,
-                                  seg_pages,
-                                  seg_pages * PAGE_SIZE / 1024);
-               }
-       }
-       seq_printf(m, "\n");
-       for (i = 0; i < dma->buf_count; i++) {
-               if (i && !(i % 32))
-                       seq_printf(m, "\n");
-               seq_printf(m, " %d", dma->buflist[i]->list);
-       }
-       seq_printf(m, "\n");
-       mutex_unlock(&dev->struct_mutex);
-       return 0;
-}
-
-/**
- * Called when "/proc/dri/.../vblank" is read.
- */
-int drm_vblank_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_device *dev = node->minor->dev;
-       int crtc;
-
-       mutex_lock(&dev->struct_mutex);
-       for (crtc = 0; crtc < dev->num_crtcs; crtc++) {
-               seq_printf(m, "CRTC %d enable:     %d\n",
-                          crtc, atomic_read(&dev->vblank_refcount[crtc]));
-               seq_printf(m, "CRTC %d counter:    %d\n",
-                          crtc, drm_vblank_count(dev, crtc));
-               seq_printf(m, "CRTC %d last wait:  %d\n",
-                          crtc, dev->last_vblank_wait[crtc]);
-               seq_printf(m, "CRTC %d in modeset: %d\n",
-                          crtc, dev->vblank_inmodeset[crtc]);
-       }
-       mutex_unlock(&dev->struct_mutex);
-       return 0;
-}
-
-/**
- * Called when "/proc/dri/.../clients" is read.
- *
- */
-int drm_clients_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_device *dev = node->minor->dev;
-       struct drm_file *priv;
-
-       mutex_lock(&dev->struct_mutex);
-       seq_printf(m, "a dev    pid    uid      magic     ioctls\n\n");
-       list_for_each_entry(priv, &dev->filelist, lhead) {
-               seq_printf(m, "%c %3d %5d %5d %10u %10lu\n",
-                          priv->authenticated ? 'y' : 'n',
-                          priv->minor->index,
-                          priv->pid,
-                          priv->uid, priv->magic, priv->ioctl_count);
-       }
-       mutex_unlock(&dev->struct_mutex);
-       return 0;
-}
-
-
-int drm_gem_one_name_info(int id, void *ptr, void *data)
-{
-       struct drm_gem_object *obj = ptr;
-       struct seq_file *m = data;
-
-       seq_printf(m, "name %d size %zd\n", obj->name, obj->size);
-
-       seq_printf(m, "%6d %8zd %7d %8d\n",
-                  obj->name, obj->size,
-                  atomic_read(&obj->handle_count),
-                  atomic_read(&obj->refcount.refcount));
-       return 0;
-}
-
-int drm_gem_name_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_device *dev = node->minor->dev;
-
-       seq_printf(m, "  name     size handles refcount\n");
-       idr_for_each(&dev->object_name_idr, drm_gem_one_name_info, m);
-       return 0;
-}
-
-#if DRM_DEBUG_CODE
-
-int drm_vma_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_device *dev = node->minor->dev;
-       struct drm_vma_entry *pt;
-       struct vm_area_struct *vma;
-#if defined(__i386__)
-       unsigned int pgprot;
-#endif
-
-       mutex_lock(&dev->struct_mutex);
-       seq_printf(m, "vma use count: %d, high_memory = %p, 0x%08llx\n",
-                  atomic_read(&dev->vma_count),
-                  high_memory, (u64)virt_to_phys(high_memory));
-
-       list_for_each_entry(pt, &dev->vmalist, head) {
-               vma = pt->vma;
-               if (!vma)
-                       continue;
-               seq_printf(m,
-                          "\n%5d 0x%08lx-0x%08lx %c%c%c%c%c%c 0x%08lx000",
-                          pt->pid, vma->vm_start, vma->vm_end,
-                          vma->vm_flags & VM_READ ? 'r' : '-',
-                          vma->vm_flags & VM_WRITE ? 'w' : '-',
-                          vma->vm_flags & VM_EXEC ? 'x' : '-',
-                          vma->vm_flags & VM_MAYSHARE ? 's' : 'p',
-                          vma->vm_flags & VM_LOCKED ? 'l' : '-',
-                          vma->vm_flags & VM_IO ? 'i' : '-',
-                          vma->vm_pgoff);
-
-#if defined(__i386__)
-               pgprot = pgprot_val(vma->vm_page_prot);
-               seq_printf(m, " %c%c%c%c%c%c%c%c%c",
-                          pgprot & _PAGE_PRESENT ? 'p' : '-',
-                          pgprot & _PAGE_RW ? 'w' : 'r',
-                          pgprot & _PAGE_USER ? 'u' : 's',
-                          pgprot & _PAGE_PWT ? 't' : 'b',
-                          pgprot & _PAGE_PCD ? 'u' : 'c',
-                          pgprot & _PAGE_ACCESSED ? 'a' : '-',
-                          pgprot & _PAGE_DIRTY ? 'd' : '-',
-                          pgprot & _PAGE_PSE ? 'm' : 'k',
-                          pgprot & _PAGE_GLOBAL ? 'g' : 'l');
-#endif
-               seq_printf(m, "\n");
-       }
-       mutex_unlock(&dev->struct_mutex);
-       return 0;
-}
-
-#endif
-
diff --git a/services4/3rdparty/linux_drm/drm_ioc32.c b/services4/3rdparty/linux_drm/drm_ioc32.c
deleted file mode 100644 (file)
index d61d185..0000000
+++ /dev/null
@@ -1,1082 +0,0 @@
-/**
- * \file drm_ioc32.c
- *
- * 32-bit ioctl compatibility routines for the DRM.
- *
- * \author Paul Mackerras <paulus@samba.org>
- *
- * Copyright (C) Paul Mackerras 2005.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * THE AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
- * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
- * IN THE SOFTWARE.
- */
-#include <linux/compat.h>
-
-#include "drmP.h"
-#include "drm_core.h"
-
-#define DRM_IOCTL_VERSION32            DRM_IOWR(0x00, drm_version32_t)
-#define DRM_IOCTL_GET_UNIQUE32         DRM_IOWR(0x01, drm_unique32_t)
-#define DRM_IOCTL_GET_MAP32            DRM_IOWR(0x04, drm_map32_t)
-#define DRM_IOCTL_GET_CLIENT32         DRM_IOWR(0x05, drm_client32_t)
-#define DRM_IOCTL_GET_STATS32          DRM_IOR( 0x06, drm_stats32_t)
-
-#define DRM_IOCTL_SET_UNIQUE32         DRM_IOW( 0x10, drm_unique32_t)
-#define DRM_IOCTL_ADD_MAP32            DRM_IOWR(0x15, drm_map32_t)
-#define DRM_IOCTL_ADD_BUFS32           DRM_IOWR(0x16, drm_buf_desc32_t)
-#define DRM_IOCTL_MARK_BUFS32          DRM_IOW( 0x17, drm_buf_desc32_t)
-#define DRM_IOCTL_INFO_BUFS32          DRM_IOWR(0x18, drm_buf_info32_t)
-#define DRM_IOCTL_MAP_BUFS32           DRM_IOWR(0x19, drm_buf_map32_t)
-#define DRM_IOCTL_FREE_BUFS32          DRM_IOW( 0x1a, drm_buf_free32_t)
-
-#define DRM_IOCTL_RM_MAP32             DRM_IOW( 0x1b, drm_map32_t)
-
-#define DRM_IOCTL_SET_SAREA_CTX32      DRM_IOW( 0x1c, drm_ctx_priv_map32_t)
-#define DRM_IOCTL_GET_SAREA_CTX32      DRM_IOWR(0x1d, drm_ctx_priv_map32_t)
-
-#define DRM_IOCTL_RES_CTX32            DRM_IOWR(0x26, drm_ctx_res32_t)
-#define DRM_IOCTL_DMA32                        DRM_IOWR(0x29, drm_dma32_t)
-
-#define DRM_IOCTL_AGP_ENABLE32         DRM_IOW( 0x32, drm_agp_mode32_t)
-#define DRM_IOCTL_AGP_INFO32           DRM_IOR( 0x33, drm_agp_info32_t)
-#define DRM_IOCTL_AGP_ALLOC32          DRM_IOWR(0x34, drm_agp_buffer32_t)
-#define DRM_IOCTL_AGP_FREE32           DRM_IOW( 0x35, drm_agp_buffer32_t)
-#define DRM_IOCTL_AGP_BIND32           DRM_IOW( 0x36, drm_agp_binding32_t)
-#define DRM_IOCTL_AGP_UNBIND32         DRM_IOW( 0x37, drm_agp_binding32_t)
-
-#define DRM_IOCTL_SG_ALLOC32           DRM_IOW( 0x38, drm_scatter_gather32_t)
-#define DRM_IOCTL_SG_FREE32            DRM_IOW( 0x39, drm_scatter_gather32_t)
-
-#define DRM_IOCTL_UPDATE_DRAW32                DRM_IOW( 0x3f, drm_update_draw32_t)
-
-#define DRM_IOCTL_WAIT_VBLANK32                DRM_IOWR(0x3a, drm_wait_vblank32_t)
-
-typedef struct drm_version_32 {
-       int version_major;        /**< Major version */
-       int version_minor;        /**< Minor version */
-       int version_patchlevel;    /**< Patch level */
-       u32 name_len;             /**< Length of name buffer */
-       u32 name;                 /**< Name of driver */
-       u32 date_len;             /**< Length of date buffer */
-       u32 date;                 /**< User-space buffer to hold date */
-       u32 desc_len;             /**< Length of desc buffer */
-       u32 desc;                 /**< User-space buffer to hold desc */
-} drm_version32_t;
-
-static int compat_drm_version(struct file *file, unsigned int cmd,
-                             unsigned long arg)
-{
-       drm_version32_t v32;
-       struct drm_version __user *version;
-       int err;
-
-       if (copy_from_user(&v32, (void __user *)arg, sizeof(v32)))
-               return -EFAULT;
-
-       version = compat_alloc_user_space(sizeof(*version));
-       if (!access_ok(VERIFY_WRITE, version, sizeof(*version)))
-               return -EFAULT;
-       if (__put_user(v32.name_len, &version->name_len)
-           || __put_user((void __user *)(unsigned long)v32.name,
-                         &version->name)
-           || __put_user(v32.date_len, &version->date_len)
-           || __put_user((void __user *)(unsigned long)v32.date,
-                         &version->date)
-           || __put_user(v32.desc_len, &version->desc_len)
-           || __put_user((void __user *)(unsigned long)v32.desc,
-                         &version->desc))
-               return -EFAULT;
-
-       err = drm_ioctl(file,
-                       DRM_IOCTL_VERSION, (unsigned long)version);
-       if (err)
-               return err;
-
-       if (__get_user(v32.version_major, &version->version_major)
-           || __get_user(v32.version_minor, &version->version_minor)
-           || __get_user(v32.version_patchlevel, &version->version_patchlevel)
-           || __get_user(v32.name_len, &version->name_len)
-           || __get_user(v32.date_len, &version->date_len)
-           || __get_user(v32.desc_len, &version->desc_len))
-               return -EFAULT;
-
-       if (copy_to_user((void __user *)arg, &v32, sizeof(v32)))
-               return -EFAULT;
-       return 0;
-}
-
-typedef struct drm_unique32 {
-       u32 unique_len; /**< Length of unique */
-       u32 unique;     /**< Unique name for driver instantiation */
-} drm_unique32_t;
-
-static int compat_drm_getunique(struct file *file, unsigned int cmd,
-                               unsigned long arg)
-{
-       drm_unique32_t uq32;
-       struct drm_unique __user *u;
-       int err;
-
-       if (copy_from_user(&uq32, (void __user *)arg, sizeof(uq32)))
-               return -EFAULT;
-
-       u = compat_alloc_user_space(sizeof(*u));
-       if (!access_ok(VERIFY_WRITE, u, sizeof(*u)))
-               return -EFAULT;
-       if (__put_user(uq32.unique_len, &u->unique_len)
-           || __put_user((void __user *)(unsigned long)uq32.unique,
-                         &u->unique))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_GET_UNIQUE, (unsigned long)u);
-       if (err)
-               return err;
-
-       if (__get_user(uq32.unique_len, &u->unique_len))
-               return -EFAULT;
-       if (copy_to_user((void __user *)arg, &uq32, sizeof(uq32)))
-               return -EFAULT;
-       return 0;
-}
-
-static int compat_drm_setunique(struct file *file, unsigned int cmd,
-                               unsigned long arg)
-{
-       drm_unique32_t uq32;
-       struct drm_unique __user *u;
-
-       if (copy_from_user(&uq32, (void __user *)arg, sizeof(uq32)))
-               return -EFAULT;
-
-       u = compat_alloc_user_space(sizeof(*u));
-       if (!access_ok(VERIFY_WRITE, u, sizeof(*u)))
-               return -EFAULT;
-       if (__put_user(uq32.unique_len, &u->unique_len)
-           || __put_user((void __user *)(unsigned long)uq32.unique,
-                         &u->unique))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_SET_UNIQUE, (unsigned long)u);
-}
-
-typedef struct drm_map32 {
-       u32 offset;             /**< Requested physical address (0 for SAREA)*/
-       u32 size;               /**< Requested physical size (bytes) */
-       enum drm_map_type type; /**< Type of memory to map */
-       enum drm_map_flags flags;       /**< Flags */
-       u32 handle;             /**< User-space: "Handle" to pass to mmap() */
-       int mtrr;               /**< MTRR slot used */
-} drm_map32_t;
-
-static int compat_drm_getmap(struct file *file, unsigned int cmd,
-                            unsigned long arg)
-{
-       drm_map32_t __user *argp = (void __user *)arg;
-       drm_map32_t m32;
-       struct drm_map __user *map;
-       int idx, err;
-       void *handle;
-
-       if (get_user(idx, &argp->offset))
-               return -EFAULT;
-
-       map = compat_alloc_user_space(sizeof(*map));
-       if (!access_ok(VERIFY_WRITE, map, sizeof(*map)))
-               return -EFAULT;
-       if (__put_user(idx, &map->offset))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_GET_MAP, (unsigned long)map);
-       if (err)
-               return err;
-
-       if (__get_user(m32.offset, &map->offset)
-           || __get_user(m32.size, &map->size)
-           || __get_user(m32.type, &map->type)
-           || __get_user(m32.flags, &map->flags)
-           || __get_user(handle, &map->handle)
-           || __get_user(m32.mtrr, &map->mtrr))
-               return -EFAULT;
-
-       m32.handle = (unsigned long)handle;
-       if (copy_to_user(argp, &m32, sizeof(m32)))
-               return -EFAULT;
-       return 0;
-
-}
-
-static int compat_drm_addmap(struct file *file, unsigned int cmd,
-                            unsigned long arg)
-{
-       drm_map32_t __user *argp = (void __user *)arg;
-       drm_map32_t m32;
-       struct drm_map __user *map;
-       int err;
-       void *handle;
-
-       if (copy_from_user(&m32, argp, sizeof(m32)))
-               return -EFAULT;
-
-       map = compat_alloc_user_space(sizeof(*map));
-       if (!access_ok(VERIFY_WRITE, map, sizeof(*map)))
-               return -EFAULT;
-       if (__put_user(m32.offset, &map->offset)
-           || __put_user(m32.size, &map->size)
-           || __put_user(m32.type, &map->type)
-           || __put_user(m32.flags, &map->flags))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_ADD_MAP, (unsigned long)map);
-       if (err)
-               return err;
-
-       if (__get_user(m32.offset, &map->offset)
-           || __get_user(m32.mtrr, &map->mtrr)
-           || __get_user(handle, &map->handle))
-               return -EFAULT;
-
-       m32.handle = (unsigned long)handle;
-       if (m32.handle != (unsigned long)handle && printk_ratelimit())
-               printk(KERN_ERR "compat_drm_addmap truncated handle"
-                      " %p for type %d offset %x\n",
-                      handle, m32.type, m32.offset);
-
-       if (copy_to_user(argp, &m32, sizeof(m32)))
-               return -EFAULT;
-
-       return 0;
-}
-
-static int compat_drm_rmmap(struct file *file, unsigned int cmd,
-                           unsigned long arg)
-{
-       drm_map32_t __user *argp = (void __user *)arg;
-       struct drm_map __user *map;
-       u32 handle;
-
-       if (get_user(handle, &argp->handle))
-               return -EFAULT;
-
-       map = compat_alloc_user_space(sizeof(*map));
-       if (!access_ok(VERIFY_WRITE, map, sizeof(*map)))
-               return -EFAULT;
-       if (__put_user((void *)(unsigned long)handle, &map->handle))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_RM_MAP, (unsigned long)map);
-}
-
-typedef struct drm_client32 {
-       int idx;        /**< Which client desired? */
-       int auth;       /**< Is client authenticated? */
-       u32 pid;        /**< Process ID */
-       u32 uid;        /**< User ID */
-       u32 magic;      /**< Magic */
-       u32 iocs;       /**< Ioctl count */
-} drm_client32_t;
-
-static int compat_drm_getclient(struct file *file, unsigned int cmd,
-                               unsigned long arg)
-{
-       drm_client32_t c32;
-       drm_client32_t __user *argp = (void __user *)arg;
-       struct drm_client __user *client;
-       int idx, err;
-
-       if (get_user(idx, &argp->idx))
-               return -EFAULT;
-
-       client = compat_alloc_user_space(sizeof(*client));
-       if (!access_ok(VERIFY_WRITE, client, sizeof(*client)))
-               return -EFAULT;
-       if (__put_user(idx, &client->idx))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_GET_CLIENT, (unsigned long)client);
-       if (err)
-               return err;
-
-       if (__get_user(c32.auth, &client->auth)
-           || __get_user(c32.pid, &client->pid)
-           || __get_user(c32.uid, &client->uid)
-           || __get_user(c32.magic, &client->magic)
-           || __get_user(c32.iocs, &client->iocs))
-               return -EFAULT;
-
-       if (copy_to_user(argp, &c32, sizeof(c32)))
-               return -EFAULT;
-       return 0;
-}
-
-typedef struct drm_stats32 {
-       u32 count;
-       struct {
-               u32 value;
-               enum drm_stat_type type;
-       } data[15];
-} drm_stats32_t;
-
-static int compat_drm_getstats(struct file *file, unsigned int cmd,
-                              unsigned long arg)
-{
-       drm_stats32_t s32;
-       drm_stats32_t __user *argp = (void __user *)arg;
-       struct drm_stats __user *stats;
-       int i, err;
-
-       stats = compat_alloc_user_space(sizeof(*stats));
-       if (!access_ok(VERIFY_WRITE, stats, sizeof(*stats)))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_GET_STATS, (unsigned long)stats);
-       if (err)
-               return err;
-
-       if (__get_user(s32.count, &stats->count))
-               return -EFAULT;
-       for (i = 0; i < 15; ++i)
-               if (__get_user(s32.data[i].value, &stats->data[i].value)
-                   || __get_user(s32.data[i].type, &stats->data[i].type))
-                       return -EFAULT;
-
-       if (copy_to_user(argp, &s32, sizeof(s32)))
-               return -EFAULT;
-       return 0;
-}
-
-typedef struct drm_buf_desc32 {
-       int count;               /**< Number of buffers of this size */
-       int size;                /**< Size in bytes */
-       int low_mark;            /**< Low water mark */
-       int high_mark;           /**< High water mark */
-       int flags;
-       u32 agp_start;           /**< Start address in the AGP aperture */
-} drm_buf_desc32_t;
-
-static int compat_drm_addbufs(struct file *file, unsigned int cmd,
-                             unsigned long arg)
-{
-       drm_buf_desc32_t __user *argp = (void __user *)arg;
-       struct drm_buf_desc __user *buf;
-       int err;
-       unsigned long agp_start;
-
-       buf = compat_alloc_user_space(sizeof(*buf));
-       if (!access_ok(VERIFY_WRITE, buf, sizeof(*buf))
-           || !access_ok(VERIFY_WRITE, argp, sizeof(*argp)))
-               return -EFAULT;
-
-       if (__copy_in_user(buf, argp, offsetof(drm_buf_desc32_t, agp_start))
-           || __get_user(agp_start, &argp->agp_start)
-           || __put_user(agp_start, &buf->agp_start))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_ADD_BUFS, (unsigned long)buf);
-       if (err)
-               return err;
-
-       if (__copy_in_user(argp, buf, offsetof(drm_buf_desc32_t, agp_start))
-           || __get_user(agp_start, &buf->agp_start)
-           || __put_user(agp_start, &argp->agp_start))
-               return -EFAULT;
-
-       return 0;
-}
-
-static int compat_drm_markbufs(struct file *file, unsigned int cmd,
-                              unsigned long arg)
-{
-       drm_buf_desc32_t b32;
-       drm_buf_desc32_t __user *argp = (void __user *)arg;
-       struct drm_buf_desc __user *buf;
-
-       if (copy_from_user(&b32, argp, sizeof(b32)))
-               return -EFAULT;
-
-       buf = compat_alloc_user_space(sizeof(*buf));
-       if (!access_ok(VERIFY_WRITE, buf, sizeof(*buf)))
-               return -EFAULT;
-
-       if (__put_user(b32.size, &buf->size)
-           || __put_user(b32.low_mark, &buf->low_mark)
-           || __put_user(b32.high_mark, &buf->high_mark))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_MARK_BUFS, (unsigned long)buf);
-}
-
-typedef struct drm_buf_info32 {
-       int count;              /**< Entries in list */
-       u32 list;
-} drm_buf_info32_t;
-
-static int compat_drm_infobufs(struct file *file, unsigned int cmd,
-                              unsigned long arg)
-{
-       drm_buf_info32_t req32;
-       drm_buf_info32_t __user *argp = (void __user *)arg;
-       drm_buf_desc32_t __user *to;
-       struct drm_buf_info __user *request;
-       struct drm_buf_desc __user *list;
-       size_t nbytes;
-       int i, err;
-       int count, actual;
-
-       if (copy_from_user(&req32, argp, sizeof(req32)))
-               return -EFAULT;
-
-       count = req32.count;
-       to = (drm_buf_desc32_t __user *) (unsigned long)req32.list;
-       if (count < 0)
-               count = 0;
-       if (count > 0
-           && !access_ok(VERIFY_WRITE, to, count * sizeof(drm_buf_desc32_t)))
-               return -EFAULT;
-
-       nbytes = sizeof(*request) + count * sizeof(struct drm_buf_desc);
-       request = compat_alloc_user_space(nbytes);
-       if (!access_ok(VERIFY_WRITE, request, nbytes))
-               return -EFAULT;
-       list = (struct drm_buf_desc *) (request + 1);
-
-       if (__put_user(count, &request->count)
-           || __put_user(list, &request->list))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_INFO_BUFS, (unsigned long)request);
-       if (err)
-               return err;
-
-       if (__get_user(actual, &request->count))
-               return -EFAULT;
-       if (count >= actual)
-               for (i = 0; i < actual; ++i)
-                       if (__copy_in_user(&to[i], &list[i],
-                                          offsetof(struct drm_buf_desc, flags)))
-                               return -EFAULT;
-
-       if (__put_user(actual, &argp->count))
-               return -EFAULT;
-
-       return 0;
-}
-
-typedef struct drm_buf_pub32 {
-       int idx;                /**< Index into the master buffer list */
-       int total;              /**< Buffer size */
-       int used;               /**< Amount of buffer in use (for DMA) */
-       u32 address;            /**< Address of buffer */
-} drm_buf_pub32_t;
-
-typedef struct drm_buf_map32 {
-       int count;              /**< Length of the buffer list */
-       u32 virtual;            /**< Mmap'd area in user-virtual */
-       u32 list;               /**< Buffer information */
-} drm_buf_map32_t;
-
-static int compat_drm_mapbufs(struct file *file, unsigned int cmd,
-                             unsigned long arg)
-{
-       drm_buf_map32_t __user *argp = (void __user *)arg;
-       drm_buf_map32_t req32;
-       drm_buf_pub32_t __user *list32;
-       struct drm_buf_map __user *request;
-       struct drm_buf_pub __user *list;
-       int i, err;
-       int count, actual;
-       size_t nbytes;
-       void __user *addr;
-
-       if (copy_from_user(&req32, argp, sizeof(req32)))
-               return -EFAULT;
-       count = req32.count;
-       list32 = (void __user *)(unsigned long)req32.list;
-
-       if (count < 0)
-               return -EINVAL;
-       nbytes = sizeof(*request) + count * sizeof(struct drm_buf_pub);
-       request = compat_alloc_user_space(nbytes);
-       if (!access_ok(VERIFY_WRITE, request, nbytes))
-               return -EFAULT;
-       list = (struct drm_buf_pub *) (request + 1);
-
-       if (__put_user(count, &request->count)
-           || __put_user(list, &request->list))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_MAP_BUFS, (unsigned long)request);
-       if (err)
-               return err;
-
-       if (__get_user(actual, &request->count))
-               return -EFAULT;
-       if (count >= actual)
-               for (i = 0; i < actual; ++i)
-                       if (__copy_in_user(&list32[i], &list[i],
-                                          offsetof(struct drm_buf_pub, address))
-                           || __get_user(addr, &list[i].address)
-                           || __put_user((unsigned long)addr,
-                                         &list32[i].address))
-                               return -EFAULT;
-
-       if (__put_user(actual, &argp->count)
-           || __get_user(addr, &request->virtual)
-           || __put_user((unsigned long)addr, &argp->virtual))
-               return -EFAULT;
-
-       return 0;
-}
-
-typedef struct drm_buf_free32 {
-       int count;
-       u32 list;
-} drm_buf_free32_t;
-
-static int compat_drm_freebufs(struct file *file, unsigned int cmd,
-                              unsigned long arg)
-{
-       drm_buf_free32_t req32;
-       struct drm_buf_free __user *request;
-       drm_buf_free32_t __user *argp = (void __user *)arg;
-
-       if (copy_from_user(&req32, argp, sizeof(req32)))
-               return -EFAULT;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request)))
-               return -EFAULT;
-       if (__put_user(req32.count, &request->count)
-           || __put_user((int __user *)(unsigned long)req32.list,
-                         &request->list))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_FREE_BUFS, (unsigned long)request);
-}
-
-typedef struct drm_ctx_priv_map32 {
-       unsigned int ctx_id;     /**< Context requesting private mapping */
-       u32 handle;             /**< Handle of map */
-} drm_ctx_priv_map32_t;
-
-static int compat_drm_setsareactx(struct file *file, unsigned int cmd,
-                                 unsigned long arg)
-{
-       drm_ctx_priv_map32_t req32;
-       struct drm_ctx_priv_map __user *request;
-       drm_ctx_priv_map32_t __user *argp = (void __user *)arg;
-
-       if (copy_from_user(&req32, argp, sizeof(req32)))
-               return -EFAULT;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request)))
-               return -EFAULT;
-       if (__put_user(req32.ctx_id, &request->ctx_id)
-           || __put_user((void *)(unsigned long)req32.handle,
-                         &request->handle))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_SET_SAREA_CTX, (unsigned long)request);
-}
-
-static int compat_drm_getsareactx(struct file *file, unsigned int cmd,
-                                 unsigned long arg)
-{
-       struct drm_ctx_priv_map __user *request;
-       drm_ctx_priv_map32_t __user *argp = (void __user *)arg;
-       int err;
-       unsigned int ctx_id;
-       void *handle;
-
-       if (!access_ok(VERIFY_WRITE, argp, sizeof(*argp))
-           || __get_user(ctx_id, &argp->ctx_id))
-               return -EFAULT;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request)))
-               return -EFAULT;
-       if (__put_user(ctx_id, &request->ctx_id))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_GET_SAREA_CTX, (unsigned long)request);
-       if (err)
-               return err;
-
-       if (__get_user(handle, &request->handle)
-           || __put_user((unsigned long)handle, &argp->handle))
-               return -EFAULT;
-
-       return 0;
-}
-
-typedef struct drm_ctx_res32 {
-       int count;
-       u32 contexts;
-} drm_ctx_res32_t;
-
-static int compat_drm_resctx(struct file *file, unsigned int cmd,
-                            unsigned long arg)
-{
-       drm_ctx_res32_t __user *argp = (void __user *)arg;
-       drm_ctx_res32_t res32;
-       struct drm_ctx_res __user *res;
-       int err;
-
-       if (copy_from_user(&res32, argp, sizeof(res32)))
-               return -EFAULT;
-
-       res = compat_alloc_user_space(sizeof(*res));
-       if (!access_ok(VERIFY_WRITE, res, sizeof(*res)))
-               return -EFAULT;
-       if (__put_user(res32.count, &res->count)
-           || __put_user((struct drm_ctx __user *) (unsigned long)res32.contexts,
-                         &res->contexts))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_RES_CTX, (unsigned long)res);
-       if (err)
-               return err;
-
-       if (__get_user(res32.count, &res->count)
-           || __put_user(res32.count, &argp->count))
-               return -EFAULT;
-
-       return 0;
-}
-
-typedef struct drm_dma32 {
-       int context;              /**< Context handle */
-       int send_count;           /**< Number of buffers to send */
-       u32 send_indices;         /**< List of handles to buffers */
-       u32 send_sizes;           /**< Lengths of data to send */
-       enum drm_dma_flags flags;                 /**< Flags */
-       int request_count;        /**< Number of buffers requested */
-       int request_size;         /**< Desired size for buffers */
-       u32 request_indices;      /**< Buffer information */
-       u32 request_sizes;
-       int granted_count;        /**< Number of buffers granted */
-} drm_dma32_t;
-
-static int compat_drm_dma(struct file *file, unsigned int cmd,
-                         unsigned long arg)
-{
-       drm_dma32_t d32;
-       drm_dma32_t __user *argp = (void __user *)arg;
-       struct drm_dma __user *d;
-       int err;
-
-       if (copy_from_user(&d32, argp, sizeof(d32)))
-               return -EFAULT;
-
-       d = compat_alloc_user_space(sizeof(*d));
-       if (!access_ok(VERIFY_WRITE, d, sizeof(*d)))
-               return -EFAULT;
-
-       if (__put_user(d32.context, &d->context)
-           || __put_user(d32.send_count, &d->send_count)
-           || __put_user((int __user *)(unsigned long)d32.send_indices,
-                         &d->send_indices)
-           || __put_user((int __user *)(unsigned long)d32.send_sizes,
-                         &d->send_sizes)
-           || __put_user(d32.flags, &d->flags)
-           || __put_user(d32.request_count, &d->request_count)
-           || __put_user((int __user *)(unsigned long)d32.request_indices,
-                         &d->request_indices)
-           || __put_user((int __user *)(unsigned long)d32.request_sizes,
-                         &d->request_sizes))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_DMA, (unsigned long)d);
-       if (err)
-               return err;
-
-       if (__get_user(d32.request_size, &d->request_size)
-           || __get_user(d32.granted_count, &d->granted_count)
-           || __put_user(d32.request_size, &argp->request_size)
-           || __put_user(d32.granted_count, &argp->granted_count))
-               return -EFAULT;
-
-       return 0;
-}
-
-#if __OS_HAS_AGP
-typedef struct drm_agp_mode32 {
-       u32 mode;       /**< AGP mode */
-} drm_agp_mode32_t;
-
-static int compat_drm_agp_enable(struct file *file, unsigned int cmd,
-                                unsigned long arg)
-{
-       drm_agp_mode32_t __user *argp = (void __user *)arg;
-       drm_agp_mode32_t m32;
-       struct drm_agp_mode __user *mode;
-
-       if (get_user(m32.mode, &argp->mode))
-               return -EFAULT;
-
-       mode = compat_alloc_user_space(sizeof(*mode));
-       if (put_user(m32.mode, &mode->mode))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_AGP_ENABLE, (unsigned long)mode);
-}
-
-typedef struct drm_agp_info32 {
-       int agp_version_major;
-       int agp_version_minor;
-       u32 mode;
-       u32 aperture_base;      /* physical address */
-       u32 aperture_size;      /* bytes */
-       u32 memory_allowed;     /* bytes */
-       u32 memory_used;
-
-       /* PCI information */
-       unsigned short id_vendor;
-       unsigned short id_device;
-} drm_agp_info32_t;
-
-static int compat_drm_agp_info(struct file *file, unsigned int cmd,
-                              unsigned long arg)
-{
-       drm_agp_info32_t __user *argp = (void __user *)arg;
-       drm_agp_info32_t i32;
-       struct drm_agp_info __user *info;
-       int err;
-
-       info = compat_alloc_user_space(sizeof(*info));
-       if (!access_ok(VERIFY_WRITE, info, sizeof(*info)))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_AGP_INFO, (unsigned long)info);
-       if (err)
-               return err;
-
-       if (__get_user(i32.agp_version_major, &info->agp_version_major)
-           || __get_user(i32.agp_version_minor, &info->agp_version_minor)
-           || __get_user(i32.mode, &info->mode)
-           || __get_user(i32.aperture_base, &info->aperture_base)
-           || __get_user(i32.aperture_size, &info->aperture_size)
-           || __get_user(i32.memory_allowed, &info->memory_allowed)
-           || __get_user(i32.memory_used, &info->memory_used)
-           || __get_user(i32.id_vendor, &info->id_vendor)
-           || __get_user(i32.id_device, &info->id_device))
-               return -EFAULT;
-
-       if (copy_to_user(argp, &i32, sizeof(i32)))
-               return -EFAULT;
-
-       return 0;
-}
-
-typedef struct drm_agp_buffer32 {
-       u32 size;       /**< In bytes -- will round to page boundary */
-       u32 handle;     /**< Used for binding / unbinding */
-       u32 type;       /**< Type of memory to allocate */
-       u32 physical;   /**< Physical used by i810 */
-} drm_agp_buffer32_t;
-
-static int compat_drm_agp_alloc(struct file *file, unsigned int cmd,
-                               unsigned long arg)
-{
-       drm_agp_buffer32_t __user *argp = (void __user *)arg;
-       drm_agp_buffer32_t req32;
-       struct drm_agp_buffer __user *request;
-       int err;
-
-       if (copy_from_user(&req32, argp, sizeof(req32)))
-               return -EFAULT;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request))
-           || __put_user(req32.size, &request->size)
-           || __put_user(req32.type, &request->type))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_AGP_ALLOC, (unsigned long)request);
-       if (err)
-               return err;
-
-       if (__get_user(req32.handle, &request->handle)
-           || __get_user(req32.physical, &request->physical)
-           || copy_to_user(argp, &req32, sizeof(req32))) {
-               drm_ioctl(file, DRM_IOCTL_AGP_FREE, (unsigned long)request);
-               return -EFAULT;
-       }
-
-       return 0;
-}
-
-static int compat_drm_agp_free(struct file *file, unsigned int cmd,
-                              unsigned long arg)
-{
-       drm_agp_buffer32_t __user *argp = (void __user *)arg;
-       struct drm_agp_buffer __user *request;
-       u32 handle;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request))
-           || get_user(handle, &argp->handle)
-           || __put_user(handle, &request->handle))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_AGP_FREE, (unsigned long)request);
-}
-
-typedef struct drm_agp_binding32 {
-       u32 handle;     /**< From drm_agp_buffer */
-       u32 offset;     /**< In bytes -- will round to page boundary */
-} drm_agp_binding32_t;
-
-static int compat_drm_agp_bind(struct file *file, unsigned int cmd,
-                              unsigned long arg)
-{
-       drm_agp_binding32_t __user *argp = (void __user *)arg;
-       drm_agp_binding32_t req32;
-       struct drm_agp_binding __user *request;
-
-       if (copy_from_user(&req32, argp, sizeof(req32)))
-               return -EFAULT;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request))
-           || __put_user(req32.handle, &request->handle)
-           || __put_user(req32.offset, &request->offset))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_AGP_BIND, (unsigned long)request);
-}
-
-static int compat_drm_agp_unbind(struct file *file, unsigned int cmd,
-                                unsigned long arg)
-{
-       drm_agp_binding32_t __user *argp = (void __user *)arg;
-       struct drm_agp_binding __user *request;
-       u32 handle;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request))
-           || get_user(handle, &argp->handle)
-           || __put_user(handle, &request->handle))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_AGP_UNBIND, (unsigned long)request);
-}
-#endif                         /* __OS_HAS_AGP */
-
-typedef struct drm_scatter_gather32 {
-       u32 size;       /**< In bytes -- will round to page boundary */
-       u32 handle;     /**< Used for mapping / unmapping */
-} drm_scatter_gather32_t;
-
-static int compat_drm_sg_alloc(struct file *file, unsigned int cmd,
-                              unsigned long arg)
-{
-       drm_scatter_gather32_t __user *argp = (void __user *)arg;
-       struct drm_scatter_gather __user *request;
-       int err;
-       unsigned long x;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request))
-           || !access_ok(VERIFY_WRITE, argp, sizeof(*argp))
-           || __get_user(x, &argp->size)
-           || __put_user(x, &request->size))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_SG_ALLOC, (unsigned long)request);
-       if (err)
-               return err;
-
-       /* XXX not sure about the handle conversion here... */
-       if (__get_user(x, &request->handle)
-           || __put_user(x >> PAGE_SHIFT, &argp->handle))
-               return -EFAULT;
-
-       return 0;
-}
-
-static int compat_drm_sg_free(struct file *file, unsigned int cmd,
-                             unsigned long arg)
-{
-       drm_scatter_gather32_t __user *argp = (void __user *)arg;
-       struct drm_scatter_gather __user *request;
-       unsigned long x;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request))
-           || !access_ok(VERIFY_WRITE, argp, sizeof(*argp))
-           || __get_user(x, &argp->handle)
-           || __put_user(x << PAGE_SHIFT, &request->handle))
-               return -EFAULT;
-
-       return drm_ioctl(file, DRM_IOCTL_SG_FREE, (unsigned long)request);
-}
-
-#if defined(CONFIG_X86) || defined(CONFIG_IA64)
-typedef struct drm_update_draw32 {
-       drm_drawable_t handle;
-       unsigned int type;
-       unsigned int num;
-       /* 64-bit version has a 32-bit pad here */
-       u64 data;       /**< Pointer */
-} __attribute__((packed)) drm_update_draw32_t;
-
-static int compat_drm_update_draw(struct file *file, unsigned int cmd,
-                                 unsigned long arg)
-{
-       drm_update_draw32_t update32;
-       struct drm_update_draw __user *request;
-       int err;
-
-       if (copy_from_user(&update32, (void __user *)arg, sizeof(update32)))
-               return -EFAULT;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request)) ||
-           __put_user(update32.handle, &request->handle) ||
-           __put_user(update32.type, &request->type) ||
-           __put_user(update32.num, &request->num) ||
-           __put_user(update32.data, &request->data))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_UPDATE_DRAW, (unsigned long)request);
-       return err;
-}
-#endif
-
-struct drm_wait_vblank_request32 {
-       enum drm_vblank_seq_type type;
-       unsigned int sequence;
-       u32 signal;
-};
-
-struct drm_wait_vblank_reply32 {
-       enum drm_vblank_seq_type type;
-       unsigned int sequence;
-       s32 tval_sec;
-       s32 tval_usec;
-};
-
-typedef union drm_wait_vblank32 {
-       struct drm_wait_vblank_request32 request;
-       struct drm_wait_vblank_reply32 reply;
-} drm_wait_vblank32_t;
-
-static int compat_drm_wait_vblank(struct file *file, unsigned int cmd,
-                                 unsigned long arg)
-{
-       drm_wait_vblank32_t __user *argp = (void __user *)arg;
-       drm_wait_vblank32_t req32;
-       union drm_wait_vblank __user *request;
-       int err;
-
-       if (copy_from_user(&req32, argp, sizeof(req32)))
-               return -EFAULT;
-
-       request = compat_alloc_user_space(sizeof(*request));
-       if (!access_ok(VERIFY_WRITE, request, sizeof(*request))
-           || __put_user(req32.request.type, &request->request.type)
-           || __put_user(req32.request.sequence, &request->request.sequence)
-           || __put_user(req32.request.signal, &request->request.signal))
-               return -EFAULT;
-
-       err = drm_ioctl(file, DRM_IOCTL_WAIT_VBLANK, (unsigned long)request);
-       if (err)
-               return err;
-
-       if (__get_user(req32.reply.type, &request->reply.type)
-           || __get_user(req32.reply.sequence, &request->reply.sequence)
-           || __get_user(req32.reply.tval_sec, &request->reply.tval_sec)
-           || __get_user(req32.reply.tval_usec, &request->reply.tval_usec))
-               return -EFAULT;
-
-       if (copy_to_user(argp, &req32, sizeof(req32)))
-               return -EFAULT;
-
-       return 0;
-}
-
-drm_ioctl_compat_t *drm_compat_ioctls[] = {
-       [DRM_IOCTL_NR(DRM_IOCTL_VERSION32)] = compat_drm_version,
-       [DRM_IOCTL_NR(DRM_IOCTL_GET_UNIQUE32)] = compat_drm_getunique,
-       [DRM_IOCTL_NR(DRM_IOCTL_GET_MAP32)] = compat_drm_getmap,
-       [DRM_IOCTL_NR(DRM_IOCTL_GET_CLIENT32)] = compat_drm_getclient,
-       [DRM_IOCTL_NR(DRM_IOCTL_GET_STATS32)] = compat_drm_getstats,
-       [DRM_IOCTL_NR(DRM_IOCTL_SET_UNIQUE32)] = compat_drm_setunique,
-       [DRM_IOCTL_NR(DRM_IOCTL_ADD_MAP32)] = compat_drm_addmap,
-       [DRM_IOCTL_NR(DRM_IOCTL_ADD_BUFS32)] = compat_drm_addbufs,
-       [DRM_IOCTL_NR(DRM_IOCTL_MARK_BUFS32)] = compat_drm_markbufs,
-       [DRM_IOCTL_NR(DRM_IOCTL_INFO_BUFS32)] = compat_drm_infobufs,
-       [DRM_IOCTL_NR(DRM_IOCTL_MAP_BUFS32)] = compat_drm_mapbufs,
-       [DRM_IOCTL_NR(DRM_IOCTL_FREE_BUFS32)] = compat_drm_freebufs,
-       [DRM_IOCTL_NR(DRM_IOCTL_RM_MAP32)] = compat_drm_rmmap,
-       [DRM_IOCTL_NR(DRM_IOCTL_SET_SAREA_CTX32)] = compat_drm_setsareactx,
-       [DRM_IOCTL_NR(DRM_IOCTL_GET_SAREA_CTX32)] = compat_drm_getsareactx,
-       [DRM_IOCTL_NR(DRM_IOCTL_RES_CTX32)] = compat_drm_resctx,
-       [DRM_IOCTL_NR(DRM_IOCTL_DMA32)] = compat_drm_dma,
-#if __OS_HAS_AGP
-       [DRM_IOCTL_NR(DRM_IOCTL_AGP_ENABLE32)] = compat_drm_agp_enable,
-       [DRM_IOCTL_NR(DRM_IOCTL_AGP_INFO32)] = compat_drm_agp_info,
-       [DRM_IOCTL_NR(DRM_IOCTL_AGP_ALLOC32)] = compat_drm_agp_alloc,
-       [DRM_IOCTL_NR(DRM_IOCTL_AGP_FREE32)] = compat_drm_agp_free,
-       [DRM_IOCTL_NR(DRM_IOCTL_AGP_BIND32)] = compat_drm_agp_bind,
-       [DRM_IOCTL_NR(DRM_IOCTL_AGP_UNBIND32)] = compat_drm_agp_unbind,
-#endif
-       [DRM_IOCTL_NR(DRM_IOCTL_SG_ALLOC32)] = compat_drm_sg_alloc,
-       [DRM_IOCTL_NR(DRM_IOCTL_SG_FREE32)] = compat_drm_sg_free,
-#if defined(CONFIG_X86) || defined(CONFIG_IA64)
-       [DRM_IOCTL_NR(DRM_IOCTL_UPDATE_DRAW32)] = compat_drm_update_draw,
-#endif
-       [DRM_IOCTL_NR(DRM_IOCTL_WAIT_VBLANK32)] = compat_drm_wait_vblank,
-};
-
-/**
- * Called whenever a 32-bit process running under a 64-bit kernel
- * performs an ioctl on /dev/drm.
- *
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument.
- * \return zero on success or negative number on failure.
- */
-long drm_compat_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
-{
-       unsigned int nr = DRM_IOCTL_NR(cmd);
-       drm_ioctl_compat_t *fn;
-       int ret;
-
-       /* Assume that ioctls without an explicit compat routine will just
-        * work.  This may not always be a good assumption, but it's better
-        * than always failing.
-        */
-       if (nr >= ARRAY_SIZE(drm_compat_ioctls))
-               return drm_ioctl(filp, cmd, arg);
-
-       fn = drm_compat_ioctls[nr];
-
-       if (fn != NULL)
-               ret = (*fn) (filp, cmd, arg);
-       else
-               ret = drm_ioctl(filp, cmd, arg);
-
-       return ret;
-}
-
-EXPORT_SYMBOL(drm_compat_ioctl);
diff --git a/services4/3rdparty/linux_drm/drm_ioctl.c b/services4/3rdparty/linux_drm/drm_ioctl.c
deleted file mode 100644 (file)
index 47db4df..0000000
+++ /dev/null
@@ -1,430 +0,0 @@
-/**
- * \file drm_ioctl.c
- * IOCTL processing for DRM
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Fri Jan  8 09:01:26 1999 by faith@valinux.com
- *
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-#include "drm_core.h"
-
-#include "linux/pci.h"
-
-/**
- * Get the bus id.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_unique structure.
- * \return zero on success or a negative number on failure.
- *
- * Copies the bus id from drm_device::unique into user space.
- */
-int drm_getunique(struct drm_device *dev, void *data,
-                 struct drm_file *file_priv)
-{
-       struct drm_unique *u = data;
-       struct drm_master *master = file_priv->master;
-
-       if (u->unique_len >= master->unique_len) {
-               if (copy_to_user(u->unique, master->unique, master->unique_len))
-                       return -EFAULT;
-       }
-       u->unique_len = master->unique_len;
-
-       return 0;
-}
-
-static void
-drm_unset_busid(struct drm_device *dev,
-               struct drm_master *master)
-{
-       kfree(dev->devname);
-       dev->devname = NULL;
-
-       kfree(master->unique);
-       master->unique = NULL;
-       master->unique_len = 0;
-       master->unique_size = 0;
-}
-
-/**
- * Set the bus id.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_unique structure.
- * \return zero on success or a negative number on failure.
- *
- * Copies the bus id from userspace into drm_device::unique, and verifies that
- * it matches the device this DRM is attached to (EINVAL otherwise).  Deprecated
- * in interface version 1.1 and will return EBUSY when setversion has requested
- * version 1.1 or greater.
- */
-int drm_setunique(struct drm_device *dev, void *data,
-                 struct drm_file *file_priv)
-{
-       struct drm_unique *u = data;
-       struct drm_master *master = file_priv->master;
-       int domain, bus, slot, func, ret;
-
-       if (master->unique_len || master->unique)
-               return -EBUSY;
-
-       if (!u->unique_len || u->unique_len > 1024)
-               return -EINVAL;
-
-       master->unique_len = u->unique_len;
-       master->unique_size = u->unique_len + 1;
-       master->unique = kmalloc(master->unique_size, GFP_KERNEL);
-       if (!master->unique) {
-               ret = -ENOMEM;
-               goto err;
-       }
-
-       if (copy_from_user(master->unique, u->unique, master->unique_len)) {
-               ret = -EFAULT;
-               goto err;
-       }
-
-       master->unique[master->unique_len] = '\0';
-
-       dev->devname = kmalloc(strlen(dev->driver->pci_driver.name) +
-                              strlen(master->unique) + 2, GFP_KERNEL);
-       if (!dev->devname) {
-               ret = -ENOMEM;
-               goto err;
-       }
-
-       sprintf(dev->devname, "%s@%s", dev->driver->pci_driver.name,
-               master->unique);
-
-       /* Return error if the busid submitted doesn't match the device's actual
-        * busid.
-        */
-       ret = sscanf(master->unique, "PCI:%d:%d:%d", &bus, &slot, &func);
-       if (ret != 3) {
-               ret = -EINVAL;
-               goto err;
-       }
-
-       domain = bus >> 8;
-       bus &= 0xff;
-
-       if ((domain != drm_get_pci_domain(dev)) ||
-           (bus != dev->pdev->bus->number) ||
-           (slot != PCI_SLOT(dev->pdev->devfn)) ||
-           (func != PCI_FUNC(dev->pdev->devfn))) {
-               ret = -EINVAL;
-               goto err;
-       }
-
-       return 0;
-
-err:
-       drm_unset_busid(dev, master);
-       return ret;
-}
-
-static int drm_set_busid(struct drm_device *dev, struct drm_file *file_priv)
-{
-       struct drm_master *master = file_priv->master;
-       int len, ret;
-
-       if (master->unique != NULL)
-               drm_unset_busid(dev, master);
-
-       if (drm_core_check_feature(dev, DRIVER_USE_PLATFORM_DEVICE)) {
-               master->unique_len = 10 + strlen(dev->platformdev->name);
-               master->unique = kmalloc(master->unique_len + 1, GFP_KERNEL);
-
-               if (master->unique == NULL)
-                       return -ENOMEM;
-
-               len = snprintf(master->unique, master->unique_len,
-                       "platform:%s", dev->platformdev->name);
-
-               if (len > master->unique_len) {
-                       DRM_ERROR("Unique buffer overflowed\n");
-                       ret = -EINVAL;
-                       goto err;
-               }
-
-               dev->devname =
-                       kmalloc(strlen(dev->platformdev->name) +
-                               master->unique_len + 2, GFP_KERNEL);
-
-               if (dev->devname == NULL) {
-                       ret = -ENOMEM;
-                       goto err;
-               }
-
-               sprintf(dev->devname, "%s@%s", dev->platformdev->name,
-                       master->unique);
-
-       } else {
-               master->unique_len = 40;
-               master->unique_size = master->unique_len;
-               master->unique = kmalloc(master->unique_size, GFP_KERNEL);
-               if (master->unique == NULL)
-                       return -ENOMEM;
-
-               len = snprintf(master->unique, master->unique_len,
-                       "pci:%04x:%02x:%02x.%d",
-                       drm_get_pci_domain(dev),
-                       dev->pdev->bus->number,
-                       PCI_SLOT(dev->pdev->devfn),
-                       PCI_FUNC(dev->pdev->devfn));
-               if (len >= master->unique_len) {
-                       DRM_ERROR("buffer overflow");
-                       ret = -EINVAL;
-                       goto err;
-               } else
-                       master->unique_len = len;
-
-               dev->devname =
-                       kmalloc(strlen(dev->driver->pci_driver.name) +
-                               master->unique_len + 2, GFP_KERNEL);
-
-               if (dev->devname == NULL) {
-                       ret = -ENOMEM;
-                       goto err;
-               }
-
-               sprintf(dev->devname, "%s@%s", dev->driver->pci_driver.name,
-                       master->unique);
-       }
-
-       return 0;
-
-err:
-       drm_unset_busid(dev, master);
-       return ret;
-}
-
-/**
- * Get a mapping information.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_map structure.
- *
- * \return zero on success or a negative number on failure.
- *
- * Searches for the mapping with the specified offset and copies its information
- * into userspace
- */
-int drm_getmap(struct drm_device *dev, void *data,
-              struct drm_file *file_priv)
-{
-       struct drm_map *map = data;
-       struct drm_map_list *r_list = NULL;
-       struct list_head *list;
-       int idx;
-       int i;
-
-       idx = map->offset;
-
-       mutex_lock(&dev->struct_mutex);
-       if (idx < 0) {
-               mutex_unlock(&dev->struct_mutex);
-               return -EINVAL;
-       }
-
-       i = 0;
-       list_for_each(list, &dev->maplist) {
-               if (i == idx) {
-                       r_list = list_entry(list, struct drm_map_list, head);
-                       break;
-               }
-               i++;
-       }
-       if (!r_list || !r_list->map) {
-               mutex_unlock(&dev->struct_mutex);
-               return -EINVAL;
-       }
-
-       map->offset = r_list->map->offset;
-       map->size = r_list->map->size;
-       map->type = r_list->map->type;
-       map->flags = r_list->map->flags;
-       map->handle = (void *)(unsigned long) r_list->user_token;
-       map->mtrr = r_list->map->mtrr;
-       mutex_unlock(&dev->struct_mutex);
-
-       return 0;
-}
-
-/**
- * Get client information.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_client structure.
- *
- * \return zero on success or a negative number on failure.
- *
- * Searches for the client with the specified index and copies its information
- * into userspace
- */
-int drm_getclient(struct drm_device *dev, void *data,
-                 struct drm_file *file_priv)
-{
-       struct drm_client *client = data;
-       struct drm_file *pt;
-       int idx;
-       int i;
-
-       idx = client->idx;
-       mutex_lock(&dev->struct_mutex);
-
-       i = 0;
-       list_for_each_entry(pt, &dev->filelist, lhead) {
-               if (i++ >= idx) {
-                       client->auth = pt->authenticated;
-                       client->pid = pt->pid;
-                       client->uid = pt->uid;
-                       client->magic = pt->magic;
-                       client->iocs = pt->ioctl_count;
-                       mutex_unlock(&dev->struct_mutex);
-
-                       return 0;
-               }
-       }
-       mutex_unlock(&dev->struct_mutex);
-
-       return -EINVAL;
-}
-
-/**
- * Get statistics information.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_stats structure.
- *
- * \return zero on success or a negative number on failure.
- */
-int drm_getstats(struct drm_device *dev, void *data,
-                struct drm_file *file_priv)
-{
-       struct drm_stats *stats = data;
-       int i;
-
-       memset(stats, 0, sizeof(*stats));
-
-       mutex_lock(&dev->struct_mutex);
-
-       for (i = 0; i < dev->counters; i++) {
-               if (dev->types[i] == _DRM_STAT_LOCK)
-                       stats->data[i].value =
-                           (file_priv->master->lock.hw_lock ? file_priv->master->lock.hw_lock->lock : 0);
-               else
-                       stats->data[i].value = atomic_read(&dev->counts[i]);
-               stats->data[i].type = dev->types[i];
-       }
-
-       stats->count = dev->counters;
-
-       mutex_unlock(&dev->struct_mutex);
-
-       return 0;
-}
-
-/**
- * Setversion ioctl.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_lock structure.
- * \return zero on success or negative number on failure.
- *
- * Sets the requested interface version
- */
-int drm_setversion(struct drm_device *dev, void *data, struct drm_file *file_priv)
-{
-       struct drm_set_version *sv = data;
-       int if_version, retcode = 0;
-
-       if (sv->drm_di_major != -1) {
-               if (sv->drm_di_major != DRM_IF_MAJOR ||
-                   sv->drm_di_minor < 0 || sv->drm_di_minor > DRM_IF_MINOR) {
-                       retcode = -EINVAL;
-                       goto done;
-               }
-               if_version = DRM_IF_VERSION(sv->drm_di_major,
-                                           sv->drm_di_minor);
-               dev->if_version = max(if_version, dev->if_version);
-               if (sv->drm_di_minor >= 1) {
-                       /*
-                        * Version 1.1 includes tying of DRM to specific device
-                        * Version 1.4 has proper PCI domain support
-                        */
-                       retcode = drm_set_busid(dev, file_priv);
-                       if (retcode)
-                               goto done;
-               }
-       }
-
-       if (sv->drm_dd_major != -1) {
-               if (sv->drm_dd_major != dev->driver->major ||
-                   sv->drm_dd_minor < 0 || sv->drm_dd_minor >
-                   dev->driver->minor) {
-                       retcode = -EINVAL;
-                       goto done;
-               }
-
-               if (dev->driver->set_version)
-                       dev->driver->set_version(dev, sv);
-       }
-
-done:
-       sv->drm_di_major = DRM_IF_MAJOR;
-       sv->drm_di_minor = DRM_IF_MINOR;
-       sv->drm_dd_major = dev->driver->major;
-       sv->drm_dd_minor = dev->driver->minor;
-
-       return retcode;
-}
-
-/** No-op ioctl. */
-int drm_noop(struct drm_device *dev, void *data,
-            struct drm_file *file_priv)
-{
-       DRM_DEBUG("\n");
-       return 0;
-}
diff --git a/services4/3rdparty/linux_drm/drm_irq.c b/services4/3rdparty/linux_drm/drm_irq.c
deleted file mode 100644 (file)
index 16d5155..0000000
+++ /dev/null
@@ -1,799 +0,0 @@
-/**
- * \file drm_irq.c
- * IRQ support
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Fri Mar 19 14:30:16 1999 by faith@valinux.com
- *
- * Copyright 1999, 2000 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-#include "drm_trace.h"
-
-#include <linux/interrupt.h>   /* For task queue support */
-#include <linux/slab.h>
-
-#include <linux/vgaarb.h>
-/**
- * Get interrupt from bus id.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_irq_busid structure.
- * \return zero on success or a negative number on failure.
- *
- * Finds the PCI device with the specified bus id and gets its IRQ number.
- * This IOCTL is deprecated, and will now return EINVAL for any busid not equal
- * to that of the device that this DRM instance attached to.
- */
-int drm_irq_by_busid(struct drm_device *dev, void *data,
-                    struct drm_file *file_priv)
-{
-       struct drm_irq_busid *p = data;
-
-       if (drm_core_check_feature(dev, DRIVER_USE_PLATFORM_DEVICE))
-               return -EINVAL;
-
-       if (!drm_core_check_feature(dev, DRIVER_HAVE_IRQ))
-               return -EINVAL;
-
-       if ((p->busnum >> 8) != drm_get_pci_domain(dev) ||
-           (p->busnum & 0xff) != dev->pdev->bus->number ||
-           p->devnum != PCI_SLOT(dev->pdev->devfn) || p->funcnum != PCI_FUNC(dev->pdev->devfn))
-               return -EINVAL;
-
-       p->irq = dev->pdev->irq;
-
-       DRM_DEBUG("%d:%d:%d => IRQ %d\n", p->busnum, p->devnum, p->funcnum,
-                 p->irq);
-
-       return 0;
-}
-
-static void vblank_disable_fn(unsigned long arg)
-{
-       struct drm_device *dev = (struct drm_device *)arg;
-       unsigned long irqflags;
-       int i;
-
-       if (!dev->vblank_disable_allowed)
-               return;
-
-       for (i = 0; i < dev->num_crtcs; i++) {
-               spin_lock_irqsave(&dev->vbl_lock, irqflags);
-               if (atomic_read(&dev->vblank_refcount[i]) == 0 &&
-                   dev->vblank_enabled[i]) {
-                       DRM_DEBUG("disabling vblank on crtc %d\n", i);
-                       dev->last_vblank[i] =
-                               dev->driver->get_vblank_counter(dev, i);
-                       dev->driver->disable_vblank(dev, i);
-                       dev->vblank_enabled[i] = 0;
-               }
-               spin_unlock_irqrestore(&dev->vbl_lock, irqflags);
-       }
-}
-
-void drm_vblank_cleanup(struct drm_device *dev)
-{
-       /* Bail if the driver didn't call drm_vblank_init() */
-       if (dev->num_crtcs == 0)
-               return;
-
-       del_timer(&dev->vblank_disable_timer);
-
-       vblank_disable_fn((unsigned long)dev);
-
-       kfree(dev->vbl_queue);
-       kfree(dev->_vblank_count);
-       kfree(dev->vblank_refcount);
-       kfree(dev->vblank_enabled);
-       kfree(dev->last_vblank);
-       kfree(dev->last_vblank_wait);
-       kfree(dev->vblank_inmodeset);
-
-       dev->num_crtcs = 0;
-}
-EXPORT_SYMBOL(drm_vblank_cleanup);
-
-int drm_vblank_init(struct drm_device *dev, int num_crtcs)
-{
-       int i, ret = -ENOMEM;
-
-       setup_timer(&dev->vblank_disable_timer, vblank_disable_fn,
-                   (unsigned long)dev);
-       spin_lock_init(&dev->vbl_lock);
-       dev->num_crtcs = num_crtcs;
-
-       dev->vbl_queue = kmalloc(sizeof(wait_queue_head_t) * num_crtcs,
-                                GFP_KERNEL);
-       if (!dev->vbl_queue)
-               goto err;
-
-       dev->_vblank_count = kmalloc(sizeof(atomic_t) * num_crtcs, GFP_KERNEL);
-       if (!dev->_vblank_count)
-               goto err;
-
-       dev->vblank_refcount = kmalloc(sizeof(atomic_t) * num_crtcs,
-                                      GFP_KERNEL);
-       if (!dev->vblank_refcount)
-               goto err;
-
-       dev->vblank_enabled = kcalloc(num_crtcs, sizeof(int), GFP_KERNEL);
-       if (!dev->vblank_enabled)
-               goto err;
-
-       dev->last_vblank = kcalloc(num_crtcs, sizeof(u32), GFP_KERNEL);
-       if (!dev->last_vblank)
-               goto err;
-
-       dev->last_vblank_wait = kcalloc(num_crtcs, sizeof(u32), GFP_KERNEL);
-       if (!dev->last_vblank_wait)
-               goto err;
-
-       dev->vblank_inmodeset = kcalloc(num_crtcs, sizeof(int), GFP_KERNEL);
-       if (!dev->vblank_inmodeset)
-               goto err;
-
-       /* Zero per-crtc vblank stuff */
-       for (i = 0; i < num_crtcs; i++) {
-               init_waitqueue_head(&dev->vbl_queue[i]);
-               atomic_set(&dev->_vblank_count[i], 0);
-               atomic_set(&dev->vblank_refcount[i], 0);
-       }
-
-       dev->vblank_disable_allowed = 0;
-       return 0;
-
-err:
-       drm_vblank_cleanup(dev);
-       return ret;
-}
-EXPORT_SYMBOL(drm_vblank_init);
-
-static void drm_irq_vgaarb_nokms(void *cookie, bool state)
-{
-       struct drm_device *dev = cookie;
-
-       if (dev->driver->vgaarb_irq) {
-               dev->driver->vgaarb_irq(dev, state);
-               return;
-       }
-
-       if (!dev->irq_enabled)
-               return;
-
-       if (state)
-               dev->driver->irq_uninstall(dev);
-       else {
-               dev->driver->irq_preinstall(dev);
-               dev->driver->irq_postinstall(dev);
-       }
-}
-
-/**
- * Install IRQ handler.
- *
- * \param dev DRM device.
- *
- * Initializes the IRQ related data. Installs the handler, calling the driver
- * \c drm_driver_irq_preinstall() and \c drm_driver_irq_postinstall() functions
- * before and after the installation.
- */
-int drm_irq_install(struct drm_device *dev)
-{
-       int ret = 0;
-       unsigned long sh_flags = 0;
-       char *irqname;
-
-       if (!drm_core_check_feature(dev, DRIVER_HAVE_IRQ))
-               return -EINVAL;
-
-       if (drm_dev_to_irq(dev) == 0)
-               return -EINVAL;
-
-       mutex_lock(&dev->struct_mutex);
-
-       /* Driver must have been initialized */
-       if (!dev->dev_private) {
-               mutex_unlock(&dev->struct_mutex);
-               return -EINVAL;
-       }
-
-       if (dev->irq_enabled) {
-               mutex_unlock(&dev->struct_mutex);
-               return -EBUSY;
-       }
-       dev->irq_enabled = 1;
-       mutex_unlock(&dev->struct_mutex);
-
-       DRM_DEBUG("irq=%d\n", drm_dev_to_irq(dev));
-
-       /* Before installing handler */
-       dev->driver->irq_preinstall(dev);
-
-       /* Install handler */
-       if (drm_core_check_feature(dev, DRIVER_IRQ_SHARED))
-               sh_flags = IRQF_SHARED;
-
-       if (dev->devname)
-               irqname = dev->devname;
-       else
-               irqname = dev->driver->name;
-
-       ret = request_irq(drm_dev_to_irq(dev), dev->driver->irq_handler,
-                         sh_flags, irqname, dev);
-
-       if (ret < 0) {
-               mutex_lock(&dev->struct_mutex);
-               dev->irq_enabled = 0;
-               mutex_unlock(&dev->struct_mutex);
-               return ret;
-       }
-
-       if (!drm_core_check_feature(dev, DRIVER_MODESET))
-               vga_client_register(dev->pdev, (void *)dev, drm_irq_vgaarb_nokms, NULL);
-
-       /* After installing handler */
-       ret = dev->driver->irq_postinstall(dev);
-       if (ret < 0) {
-               mutex_lock(&dev->struct_mutex);
-               dev->irq_enabled = 0;
-               mutex_unlock(&dev->struct_mutex);
-       }
-
-       return ret;
-}
-EXPORT_SYMBOL(drm_irq_install);
-
-/**
- * Uninstall the IRQ handler.
- *
- * \param dev DRM device.
- *
- * Calls the driver's \c drm_driver_irq_uninstall() function, and stops the irq.
- */
-int drm_irq_uninstall(struct drm_device * dev)
-{
-       unsigned long irqflags;
-       int irq_enabled, i;
-
-       if (!drm_core_check_feature(dev, DRIVER_HAVE_IRQ))
-               return -EINVAL;
-
-       mutex_lock(&dev->struct_mutex);
-       irq_enabled = dev->irq_enabled;
-       dev->irq_enabled = 0;
-       mutex_unlock(&dev->struct_mutex);
-
-       /*
-        * Wake up any waiters so they don't hang.
-        */
-       spin_lock_irqsave(&dev->vbl_lock, irqflags);
-       for (i = 0; i < dev->num_crtcs; i++) {
-               DRM_WAKEUP(&dev->vbl_queue[i]);
-               dev->vblank_enabled[i] = 0;
-               dev->last_vblank[i] = dev->driver->get_vblank_counter(dev, i);
-       }
-       spin_unlock_irqrestore(&dev->vbl_lock, irqflags);
-
-       if (!irq_enabled)
-               return -EINVAL;
-
-       DRM_DEBUG("irq=%d\n", drm_dev_to_irq(dev));
-
-       if (!drm_core_check_feature(dev, DRIVER_MODESET))
-               vga_client_register(dev->pdev, NULL, NULL, NULL);
-
-       dev->driver->irq_uninstall(dev);
-
-       free_irq(drm_dev_to_irq(dev), dev);
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_irq_uninstall);
-
-/**
- * IRQ control ioctl.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_control structure.
- * \return zero on success or a negative number on failure.
- *
- * Calls irq_install() or irq_uninstall() according to \p arg.
- */
-int drm_control(struct drm_device *dev, void *data,
-               struct drm_file *file_priv)
-{
-       struct drm_control *ctl = data;
-
-       /* if we haven't irq we fallback for compatibility reasons - this used to be a separate function in drm_dma.h */
-
-
-       switch (ctl->func) {
-       case DRM_INST_HANDLER:
-               if (!drm_core_check_feature(dev, DRIVER_HAVE_IRQ))
-                       return 0;
-               if (drm_core_check_feature(dev, DRIVER_MODESET))
-                       return 0;
-               if (dev->if_version < DRM_IF_VERSION(1, 2) &&
-                   ctl->irq != drm_dev_to_irq(dev))
-                       return -EINVAL;
-               return drm_irq_install(dev);
-       case DRM_UNINST_HANDLER:
-               if (!drm_core_check_feature(dev, DRIVER_HAVE_IRQ))
-                       return 0;
-               if (drm_core_check_feature(dev, DRIVER_MODESET))
-                       return 0;
-               return drm_irq_uninstall(dev);
-       default:
-               return -EINVAL;
-       }
-}
-
-/**
- * drm_vblank_count - retrieve "cooked" vblank counter value
- * @dev: DRM device
- * @crtc: which counter to retrieve
- *
- * Fetches the "cooked" vblank count value that represents the number of
- * vblank events since the system was booted, including lost events due to
- * modesetting activity.
- */
-u32 drm_vblank_count(struct drm_device *dev, int crtc)
-{
-       return atomic_read(&dev->_vblank_count[crtc]);
-}
-EXPORT_SYMBOL(drm_vblank_count);
-
-/**
- * drm_update_vblank_count - update the master vblank counter
- * @dev: DRM device
- * @crtc: counter to update
- *
- * Call back into the driver to update the appropriate vblank counter
- * (specified by @crtc).  Deal with wraparound, if it occurred, and
- * update the last read value so we can deal with wraparound on the next
- * call if necessary.
- *
- * Only necessary when going from off->on, to account for frames we
- * didn't get an interrupt for.
- *
- * Note: caller must hold dev->vbl_lock since this reads & writes
- * device vblank fields.
- */
-static void drm_update_vblank_count(struct drm_device *dev, int crtc)
-{
-       u32 cur_vblank, diff;
-
-       /*
-        * Interrupts were disabled prior to this call, so deal with counter
-        * wrap if needed.
-        * NOTE!  It's possible we lost a full dev->max_vblank_count events
-        * here if the register is small or we had vblank interrupts off for
-        * a long time.
-        */
-       cur_vblank = dev->driver->get_vblank_counter(dev, crtc);
-       diff = cur_vblank - dev->last_vblank[crtc];
-       if (cur_vblank < dev->last_vblank[crtc]) {
-               diff += dev->max_vblank_count;
-
-               DRM_DEBUG("last_vblank[%d]=0x%x, cur_vblank=0x%x => diff=0x%x\n",
-                         crtc, dev->last_vblank[crtc], cur_vblank, diff);
-       }
-
-       DRM_DEBUG("enabling vblank interrupts on crtc %d, missed %d\n",
-                 crtc, diff);
-
-       atomic_add(diff, &dev->_vblank_count[crtc]);
-}
-
-/**
- * drm_vblank_get - get a reference count on vblank events
- * @dev: DRM device
- * @crtc: which CRTC to own
- *
- * Acquire a reference count on vblank events to avoid having them disabled
- * while in use.
- *
- * RETURNS
- * Zero on success, nonzero on failure.
- */
-int drm_vblank_get(struct drm_device *dev, int crtc)
-{
-       unsigned long irqflags;
-       int ret = 0;
-
-       spin_lock_irqsave(&dev->vbl_lock, irqflags);
-       /* Going from 0->1 means we have to enable interrupts again */
-       if (atomic_add_return(1, &dev->vblank_refcount[crtc]) == 1) {
-               if (!dev->vblank_enabled[crtc]) {
-                       ret = dev->driver->enable_vblank(dev, crtc);
-                       DRM_DEBUG("enabling vblank on crtc %d, ret: %d\n", crtc, ret);
-                       if (ret)
-                               atomic_dec(&dev->vblank_refcount[crtc]);
-                       else {
-                               dev->vblank_enabled[crtc] = 1;
-                               drm_update_vblank_count(dev, crtc);
-                       }
-               }
-       } else {
-               if (!dev->vblank_enabled[crtc]) {
-                       atomic_dec(&dev->vblank_refcount[crtc]);
-                       ret = -EINVAL;
-               }
-       }
-       spin_unlock_irqrestore(&dev->vbl_lock, irqflags);
-
-       return ret;
-}
-EXPORT_SYMBOL(drm_vblank_get);
-
-/**
- * drm_vblank_put - give up ownership of vblank events
- * @dev: DRM device
- * @crtc: which counter to give up
- *
- * Release ownership of a given vblank counter, turning off interrupts
- * if possible.
- */
-void drm_vblank_put(struct drm_device *dev, int crtc)
-{
-       BUG_ON (atomic_read (&dev->vblank_refcount[crtc]) == 0);
-
-       /* Last user schedules interrupt disable */
-       if (atomic_dec_and_test(&dev->vblank_refcount[crtc]))
-               mod_timer(&dev->vblank_disable_timer, jiffies + 5*DRM_HZ);
-}
-EXPORT_SYMBOL(drm_vblank_put);
-
-void drm_vblank_off(struct drm_device *dev, int crtc)
-{
-       unsigned long irqflags;
-
-       spin_lock_irqsave(&dev->vbl_lock, irqflags);
-       dev->driver->disable_vblank(dev, crtc);
-       DRM_WAKEUP(&dev->vbl_queue[crtc]);
-       dev->vblank_enabled[crtc] = 0;
-       dev->last_vblank[crtc] = dev->driver->get_vblank_counter(dev, crtc);
-       spin_unlock_irqrestore(&dev->vbl_lock, irqflags);
-}
-EXPORT_SYMBOL(drm_vblank_off);
-
-/**
- * drm_vblank_pre_modeset - account for vblanks across mode sets
- * @dev: DRM device
- * @crtc: CRTC in question
- * @post: post or pre mode set?
- *
- * Account for vblank events across mode setting events, which will likely
- * reset the hardware frame counter.
- */
-void drm_vblank_pre_modeset(struct drm_device *dev, int crtc)
-{
-       /* vblank is not initialized (IRQ not installed ?) */
-       if (!dev->num_crtcs)
-               return;
-       /*
-        * To avoid all the problems that might happen if interrupts
-        * were enabled/disabled around or between these calls, we just
-        * have the kernel take a reference on the CRTC (just once though
-        * to avoid corrupting the count if multiple, mismatch calls occur),
-        * so that interrupts remain enabled in the interim.
-        */
-       if (!dev->vblank_inmodeset[crtc]) {
-               dev->vblank_inmodeset[crtc] = 0x1;
-               if (drm_vblank_get(dev, crtc) == 0)
-                       dev->vblank_inmodeset[crtc] |= 0x2;
-       }
-}
-EXPORT_SYMBOL(drm_vblank_pre_modeset);
-
-void drm_vblank_post_modeset(struct drm_device *dev, int crtc)
-{
-       unsigned long irqflags;
-
-       if (dev->vblank_inmodeset[crtc]) {
-               spin_lock_irqsave(&dev->vbl_lock, irqflags);
-               dev->vblank_disable_allowed = 1;
-               spin_unlock_irqrestore(&dev->vbl_lock, irqflags);
-
-               if (dev->vblank_inmodeset[crtc] & 0x2)
-                       drm_vblank_put(dev, crtc);
-
-               dev->vblank_inmodeset[crtc] = 0;
-       }
-}
-EXPORT_SYMBOL(drm_vblank_post_modeset);
-
-/**
- * drm_modeset_ctl - handle vblank event counter changes across mode switch
- * @DRM_IOCTL_ARGS: standard ioctl arguments
- *
- * Applications should call the %_DRM_PRE_MODESET and %_DRM_POST_MODESET
- * ioctls around modesetting so that any lost vblank events are accounted for.
- *
- * Generally the counter will reset across mode sets.  If interrupts are
- * enabled around this call, we don't have to do anything since the counter
- * will have already been incremented.
- */
-int drm_modeset_ctl(struct drm_device *dev, void *data,
-                   struct drm_file *file_priv)
-{
-       struct drm_modeset_ctl *modeset = data;
-       int crtc, ret = 0;
-
-       /* If drm_vblank_init() hasn't been called yet, just no-op */
-       if (!dev->num_crtcs)
-               goto out;
-
-       crtc = modeset->crtc;
-       if (crtc >= dev->num_crtcs) {
-               ret = -EINVAL;
-               goto out;
-       }
-
-       switch (modeset->cmd) {
-       case _DRM_PRE_MODESET:
-               drm_vblank_pre_modeset(dev, crtc);
-               break;
-       case _DRM_POST_MODESET:
-               drm_vblank_post_modeset(dev, crtc);
-               break;
-       default:
-               ret = -EINVAL;
-               break;
-       }
-
-out:
-       return ret;
-}
-
-static int drm_queue_vblank_event(struct drm_device *dev, int pipe,
-                                 union drm_wait_vblank *vblwait,
-                                 struct drm_file *file_priv)
-{
-       struct drm_pending_vblank_event *e;
-       struct timeval now;
-       unsigned long flags;
-       unsigned int seq;
-       int ret;
-
-       e = kzalloc(sizeof *e, GFP_KERNEL);
-       if (e == NULL) {
-               ret = -ENOMEM;
-               goto err_put;
-       }
-
-       e->pipe = pipe;
-       e->base.pid = current->pid;
-       e->event.base.type = DRM_EVENT_VBLANK;
-       e->event.base.length = sizeof e->event;
-       e->event.user_data = vblwait->request.signal;
-       e->base.event = &e->event.base;
-       e->base.file_priv = file_priv;
-       e->base.destroy = (void (*) (struct drm_pending_event *)) kfree;
-
-       do_gettimeofday(&now);
-       spin_lock_irqsave(&dev->event_lock, flags);
-
-       if (file_priv->event_space < sizeof e->event) {
-               ret = -EBUSY;
-               goto err_unlock;
-       }
-
-       file_priv->event_space -= sizeof e->event;
-       seq = drm_vblank_count(dev, pipe);
-       if ((vblwait->request.type & _DRM_VBLANK_NEXTONMISS) &&
-           (seq - vblwait->request.sequence) <= (1 << 23)) {
-               vblwait->request.sequence = seq + 1;
-               vblwait->reply.sequence = vblwait->request.sequence;
-       }
-
-       DRM_DEBUG("event on vblank count %d, current %d, crtc %d\n",
-                 vblwait->request.sequence, seq, pipe);
-
-       trace_drm_vblank_event_queued(current->pid, pipe,
-                                     vblwait->request.sequence);
-
-       e->event.sequence = vblwait->request.sequence;
-       if ((seq - vblwait->request.sequence) <= (1 << 23)) {
-               e->event.tv_sec = now.tv_sec;
-               e->event.tv_usec = now.tv_usec;
-               drm_vblank_put(dev, pipe);
-               list_add_tail(&e->base.link, &e->base.file_priv->event_list);
-               wake_up_interruptible(&e->base.file_priv->event_wait);
-               trace_drm_vblank_event_delivered(current->pid, pipe,
-                                                vblwait->request.sequence);
-       } else {
-               list_add_tail(&e->base.link, &dev->vblank_event_list);
-       }
-
-       spin_unlock_irqrestore(&dev->event_lock, flags);
-
-       return 0;
-
-err_unlock:
-       spin_unlock_irqrestore(&dev->event_lock, flags);
-       kfree(e);
-err_put:
-       drm_vblank_put(dev, pipe);
-       return ret;
-}
-
-/**
- * Wait for VBLANK.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param data user argument, pointing to a drm_wait_vblank structure.
- * \return zero on success or a negative number on failure.
- *
- * This function enables the vblank interrupt on the pipe requested, then
- * sleeps waiting for the requested sequence number to occur, and drops
- * the vblank interrupt refcount afterwards. (vblank irq disable follows that
- * after a timeout with no further vblank waits scheduled).
- */
-int drm_wait_vblank(struct drm_device *dev, void *data,
-                   struct drm_file *file_priv)
-{
-       union drm_wait_vblank *vblwait = data;
-       int ret = 0;
-       unsigned int flags, seq, crtc;
-
-       if ((!drm_dev_to_irq(dev)) || (!dev->irq_enabled))
-               return -EINVAL;
-
-       if (vblwait->request.type & _DRM_VBLANK_SIGNAL)
-               return -EINVAL;
-
-       if (vblwait->request.type &
-           ~(_DRM_VBLANK_TYPES_MASK | _DRM_VBLANK_FLAGS_MASK)) {
-               DRM_ERROR("Unsupported type value 0x%x, supported mask 0x%x\n",
-                         vblwait->request.type,
-                         (_DRM_VBLANK_TYPES_MASK | _DRM_VBLANK_FLAGS_MASK));
-               return -EINVAL;
-       }
-
-       flags = vblwait->request.type & _DRM_VBLANK_FLAGS_MASK;
-       crtc = flags & _DRM_VBLANK_SECONDARY ? 1 : 0;
-
-       if (crtc >= dev->num_crtcs)
-               return -EINVAL;
-
-       ret = drm_vblank_get(dev, crtc);
-       if (ret) {
-               DRM_DEBUG("failed to acquire vblank counter, %d\n", ret);
-               return ret;
-       }
-       seq = drm_vblank_count(dev, crtc);
-
-       switch (vblwait->request.type & _DRM_VBLANK_TYPES_MASK) {
-       case _DRM_VBLANK_RELATIVE:
-               vblwait->request.sequence += seq;
-               vblwait->request.type &= ~_DRM_VBLANK_RELATIVE;
-       case _DRM_VBLANK_ABSOLUTE:
-               break;
-       default:
-               ret = -EINVAL;
-               goto done;
-       }
-
-       if (flags & _DRM_VBLANK_EVENT)
-               return drm_queue_vblank_event(dev, crtc, vblwait, file_priv);
-
-       if ((flags & _DRM_VBLANK_NEXTONMISS) &&
-           (seq - vblwait->request.sequence) <= (1<<23)) {
-               vblwait->request.sequence = seq + 1;
-       }
-
-       DRM_DEBUG("waiting on vblank count %d, crtc %d\n",
-                 vblwait->request.sequence, crtc);
-       dev->last_vblank_wait[crtc] = vblwait->request.sequence;
-       DRM_WAIT_ON(ret, dev->vbl_queue[crtc], 3 * DRM_HZ,
-                   (((drm_vblank_count(dev, crtc) -
-                      vblwait->request.sequence) <= (1 << 23)) ||
-                    !dev->irq_enabled));
-
-       if (ret != -EINTR) {
-               struct timeval now;
-
-               do_gettimeofday(&now);
-
-               vblwait->reply.tval_sec = now.tv_sec;
-               vblwait->reply.tval_usec = now.tv_usec;
-               vblwait->reply.sequence = drm_vblank_count(dev, crtc);
-               DRM_DEBUG("returning %d to client\n",
-                         vblwait->reply.sequence);
-       } else {
-               DRM_DEBUG("vblank wait interrupted by signal\n");
-       }
-
-done:
-       drm_vblank_put(dev, crtc);
-       return ret;
-}
-
-void drm_handle_vblank_events(struct drm_device *dev, int crtc)
-{
-       struct drm_pending_vblank_event *e, *t;
-       struct timeval now;
-       unsigned long flags;
-       unsigned int seq;
-
-       do_gettimeofday(&now);
-       seq = drm_vblank_count(dev, crtc);
-
-       spin_lock_irqsave(&dev->event_lock, flags);
-
-       list_for_each_entry_safe(e, t, &dev->vblank_event_list, base.link) {
-               if (e->pipe != crtc)
-                       continue;
-               if ((seq - e->event.sequence) > (1<<23))
-                       continue;
-
-               DRM_DEBUG("vblank event on %d, current %d\n",
-                         e->event.sequence, seq);
-
-               e->event.sequence = seq;
-               e->event.tv_sec = now.tv_sec;
-               e->event.tv_usec = now.tv_usec;
-               drm_vblank_put(dev, e->pipe);
-               list_move_tail(&e->base.link, &e->base.file_priv->event_list);
-               wake_up_interruptible(&e->base.file_priv->event_wait);
-               trace_drm_vblank_event_delivered(e->base.pid, e->pipe,
-                                                e->event.sequence);
-       }
-
-       spin_unlock_irqrestore(&dev->event_lock, flags);
-
-       trace_drm_vblank_event(crtc, seq);
-}
-
-/**
- * drm_handle_vblank - handle a vblank event
- * @dev: DRM device
- * @crtc: where this event occurred
- *
- * Drivers should call this routine in their vblank interrupt handlers to
- * update the vblank counter and send any signals that may be pending.
- */
-void drm_handle_vblank(struct drm_device *dev, int crtc)
-{
-       if (!dev->num_crtcs)
-               return;
-
-       atomic_inc(&dev->_vblank_count[crtc]);
-       DRM_WAKEUP(&dev->vbl_queue[crtc]);
-       drm_handle_vblank_events(dev, crtc);
-}
-EXPORT_SYMBOL(drm_handle_vblank);
diff --git a/services4/3rdparty/linux_drm/drm_lock.c b/services4/3rdparty/linux_drm/drm_lock.c
deleted file mode 100644 (file)
index 632ae24..0000000
+++ /dev/null
@@ -1,374 +0,0 @@
-/**
- * \file drm_lock.c
- * IOCTLs for locking
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Tue Feb  2 08:37:54 1999 by faith@valinux.com
- *
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-
-static int drm_notifier(void *priv);
-
-static int drm_lock_take(struct drm_lock_data *lock_data, unsigned int context);
-
-/**
- * Lock ioctl.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_lock structure.
- * \return zero on success or negative number on failure.
- *
- * Add the current task to the lock wait queue, and attempt to take to lock.
- */
-int drm_lock(struct drm_device *dev, void *data, struct drm_file *file_priv)
-{
-       DECLARE_WAITQUEUE(entry, current);
-       struct drm_lock *lock = data;
-       struct drm_master *master = file_priv->master;
-       int ret = 0;
-
-       ++file_priv->lock_count;
-
-       if (lock->context == DRM_KERNEL_CONTEXT) {
-               DRM_ERROR("Process %d using kernel context %d\n",
-                         task_pid_nr(current), lock->context);
-               return -EINVAL;
-       }
-
-       DRM_DEBUG("%d (pid %d) requests lock (0x%08x), flags = 0x%08x\n",
-                 lock->context, task_pid_nr(current),
-                 master->lock.hw_lock->lock, lock->flags);
-
-       if (drm_core_check_feature(dev, DRIVER_DMA_QUEUE))
-               if (lock->context < 0)
-                       return -EINVAL;
-
-       add_wait_queue(&master->lock.lock_queue, &entry);
-       spin_lock_bh(&master->lock.spinlock);
-       master->lock.user_waiters++;
-       spin_unlock_bh(&master->lock.spinlock);
-
-       for (;;) {
-               __set_current_state(TASK_INTERRUPTIBLE);
-               if (!master->lock.hw_lock) {
-                       /* Device has been unregistered */
-                       send_sig(SIGTERM, current, 0);
-                       ret = -EINTR;
-                       break;
-               }
-               if (drm_lock_take(&master->lock, lock->context)) {
-                       master->lock.file_priv = file_priv;
-                       master->lock.lock_time = jiffies;
-                       atomic_inc(&dev->counts[_DRM_STAT_LOCKS]);
-                       break;  /* Got lock */
-               }
-
-               /* Contention */
-               mutex_unlock(&drm_global_mutex);
-               schedule();
-               mutex_lock(&drm_global_mutex);
-               if (signal_pending(current)) {
-                       ret = -EINTR;
-                       break;
-               }
-       }
-       spin_lock_bh(&master->lock.spinlock);
-       master->lock.user_waiters--;
-       spin_unlock_bh(&master->lock.spinlock);
-       __set_current_state(TASK_RUNNING);
-       remove_wait_queue(&master->lock.lock_queue, &entry);
-
-       DRM_DEBUG("%d %s\n", lock->context,
-                 ret ? "interrupted" : "has lock");
-       if (ret) return ret;
-
-       /* don't set the block all signals on the master process for now 
-        * really probably not the correct answer but lets us debug xkb
-        * xserver for now */
-       if (!file_priv->is_master) {
-               sigemptyset(&dev->sigmask);
-               sigaddset(&dev->sigmask, SIGSTOP);
-               sigaddset(&dev->sigmask, SIGTSTP);
-               sigaddset(&dev->sigmask, SIGTTIN);
-               sigaddset(&dev->sigmask, SIGTTOU);
-               dev->sigdata.context = lock->context;
-               dev->sigdata.lock = master->lock.hw_lock;
-               block_all_signals(drm_notifier, &dev->sigdata, &dev->sigmask);
-       }
-
-       if (dev->driver->dma_quiescent && (lock->flags & _DRM_LOCK_QUIESCENT))
-       {
-               if (dev->driver->dma_quiescent(dev)) {
-                       DRM_DEBUG("%d waiting for DMA quiescent\n",
-                                 lock->context);
-                       return -EBUSY;
-               }
-       }
-
-       return 0;
-}
-
-/**
- * Unlock ioctl.
- *
- * \param inode device inode.
- * \param file_priv DRM file private.
- * \param cmd command.
- * \param arg user argument, pointing to a drm_lock structure.
- * \return zero on success or negative number on failure.
- *
- * Transfer and free the lock.
- */
-int drm_unlock(struct drm_device *dev, void *data, struct drm_file *file_priv)
-{
-       struct drm_lock *lock = data;
-       struct drm_master *master = file_priv->master;
-
-       if (lock->context == DRM_KERNEL_CONTEXT) {
-               DRM_ERROR("Process %d using kernel context %d\n",
-                         task_pid_nr(current), lock->context);
-               return -EINVAL;
-       }
-
-       atomic_inc(&dev->counts[_DRM_STAT_UNLOCKS]);
-
-       if (drm_lock_free(&master->lock, lock->context)) {
-               /* FIXME: Should really bail out here. */
-       }
-
-       unblock_all_signals();
-       return 0;
-}
-
-/**
- * Take the heavyweight lock.
- *
- * \param lock lock pointer.
- * \param context locking context.
- * \return one if the lock is held, or zero otherwise.
- *
- * Attempt to mark the lock as held by the given context, via the \p cmpxchg instruction.
- */
-static
-int drm_lock_take(struct drm_lock_data *lock_data,
-                 unsigned int context)
-{
-       unsigned int old, new, prev;
-       volatile unsigned int *lock = &lock_data->hw_lock->lock;
-
-       spin_lock_bh(&lock_data->spinlock);
-       do {
-               old = *lock;
-               if (old & _DRM_LOCK_HELD)
-                       new = old | _DRM_LOCK_CONT;
-               else {
-                       new = context | _DRM_LOCK_HELD |
-                               ((lock_data->user_waiters + lock_data->kernel_waiters > 1) ?
-                                _DRM_LOCK_CONT : 0);
-               }
-               prev = cmpxchg(lock, old, new);
-       } while (prev != old);
-       spin_unlock_bh(&lock_data->spinlock);
-
-       if (_DRM_LOCKING_CONTEXT(old) == context) {
-               if (old & _DRM_LOCK_HELD) {
-                       if (context != DRM_KERNEL_CONTEXT) {
-                               DRM_ERROR("%d holds heavyweight lock\n",
-                                         context);
-                       }
-                       return 0;
-               }
-       }
-
-       if ((_DRM_LOCKING_CONTEXT(new)) == context && (new & _DRM_LOCK_HELD)) {
-               /* Have lock */
-               return 1;
-       }
-       return 0;
-}
-
-/**
- * This takes a lock forcibly and hands it to context. Should ONLY be used
- * inside *_unlock to give lock to kernel before calling *_dma_schedule.
- *
- * \param dev DRM device.
- * \param lock lock pointer.
- * \param context locking context.
- * \return always one.
- *
- * Resets the lock file pointer.
- * Marks the lock as held by the given context, via the \p cmpxchg instruction.
- */
-static int drm_lock_transfer(struct drm_lock_data *lock_data,
-                            unsigned int context)
-{
-       unsigned int old, new, prev;
-       volatile unsigned int *lock = &lock_data->hw_lock->lock;
-
-       lock_data->file_priv = NULL;
-       do {
-               old = *lock;
-               new = context | _DRM_LOCK_HELD;
-               prev = cmpxchg(lock, old, new);
-       } while (prev != old);
-       return 1;
-}
-
-/**
- * Free lock.
- *
- * \param dev DRM device.
- * \param lock lock.
- * \param context context.
- *
- * Resets the lock file pointer.
- * Marks the lock as not held, via the \p cmpxchg instruction. Wakes any task
- * waiting on the lock queue.
- */
-int drm_lock_free(struct drm_lock_data *lock_data, unsigned int context)
-{
-       unsigned int old, new, prev;
-       volatile unsigned int *lock = &lock_data->hw_lock->lock;
-
-       spin_lock_bh(&lock_data->spinlock);
-       if (lock_data->kernel_waiters != 0) {
-               drm_lock_transfer(lock_data, 0);
-               lock_data->idle_has_lock = 1;
-               spin_unlock_bh(&lock_data->spinlock);
-               return 1;
-       }
-       spin_unlock_bh(&lock_data->spinlock);
-
-       do {
-               old = *lock;
-               new = _DRM_LOCKING_CONTEXT(old);
-               prev = cmpxchg(lock, old, new);
-       } while (prev != old);
-
-       if (_DRM_LOCK_IS_HELD(old) && _DRM_LOCKING_CONTEXT(old) != context) {
-               DRM_ERROR("%d freed heavyweight lock held by %d\n",
-                         context, _DRM_LOCKING_CONTEXT(old));
-               return 1;
-       }
-       wake_up_interruptible(&lock_data->lock_queue);
-       return 0;
-}
-
-/**
- * If we get here, it means that the process has called DRM_IOCTL_LOCK
- * without calling DRM_IOCTL_UNLOCK.
- *
- * If the lock is not held, then let the signal proceed as usual.  If the lock
- * is held, then set the contended flag and keep the signal blocked.
- *
- * \param priv pointer to a drm_sigdata structure.
- * \return one if the signal should be delivered normally, or zero if the
- * signal should be blocked.
- */
-static int drm_notifier(void *priv)
-{
-       struct drm_sigdata *s = (struct drm_sigdata *) priv;
-       unsigned int old, new, prev;
-
-       /* Allow signal delivery if lock isn't held */
-       if (!s->lock || !_DRM_LOCK_IS_HELD(s->lock->lock)
-           || _DRM_LOCKING_CONTEXT(s->lock->lock) != s->context)
-               return 1;
-
-       /* Otherwise, set flag to force call to
-          drmUnlock */
-       do {
-               old = s->lock->lock;
-               new = old | _DRM_LOCK_CONT;
-               prev = cmpxchg(&s->lock->lock, old, new);
-       } while (prev != old);
-       return 0;
-}
-
-/**
- * This function returns immediately and takes the hw lock
- * with the kernel context if it is free, otherwise it gets the highest priority when and if
- * it is eventually released.
- *
- * This guarantees that the kernel will _eventually_ have the lock _unless_ it is held
- * by a blocked process. (In the latter case an explicit wait for the hardware lock would cause
- * a deadlock, which is why the "idlelock" was invented).
- *
- * This should be sufficient to wait for GPU idle without
- * having to worry about starvation.
- */
-
-void drm_idlelock_take(struct drm_lock_data *lock_data)
-{
-       int ret = 0;
-
-       spin_lock_bh(&lock_data->spinlock);
-       lock_data->kernel_waiters++;
-       if (!lock_data->idle_has_lock) {
-
-               spin_unlock_bh(&lock_data->spinlock);
-               ret = drm_lock_take(lock_data, DRM_KERNEL_CONTEXT);
-               spin_lock_bh(&lock_data->spinlock);
-
-               if (ret == 1)
-                       lock_data->idle_has_lock = 1;
-       }
-       spin_unlock_bh(&lock_data->spinlock);
-}
-
-void drm_idlelock_release(struct drm_lock_data *lock_data)
-{
-       unsigned int old, prev;
-       volatile unsigned int *lock = &lock_data->hw_lock->lock;
-
-       spin_lock_bh(&lock_data->spinlock);
-       if (--lock_data->kernel_waiters == 0) {
-               if (lock_data->idle_has_lock) {
-                       do {
-                               old = *lock;
-                               prev = cmpxchg(lock, old, DRM_KERNEL_CONTEXT);
-                       } while (prev != old);
-                       wake_up_interruptible(&lock_data->lock_queue);
-                       lock_data->idle_has_lock = 0;
-               }
-       }
-       spin_unlock_bh(&lock_data->spinlock);
-}
-
-int drm_i_have_hw_lock(struct drm_device *dev, struct drm_file *file_priv)
-{
-       struct drm_master *master = file_priv->master;
-       return (file_priv->lock_count && master->lock.hw_lock &&
-               _DRM_LOCK_IS_HELD(master->lock.hw_lock->lock) &&
-               master->lock.file_priv == file_priv);
-}
diff --git a/services4/3rdparty/linux_drm/drm_memory.c b/services4/3rdparty/linux_drm/drm_memory.c
deleted file mode 100644 (file)
index c9b8050..0000000
+++ /dev/null
@@ -1,162 +0,0 @@
-/**
- * \file drm_memory.c
- * Memory management wrappers for DRM
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Thu Feb  4 14:00:34 1999 by faith@valinux.com
- *
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/highmem.h>
-#include "drmP.h"
-
-/**
- * Called when "/proc/dri/%dev%/mem" is read.
- *
- * \param buf output buffer.
- * \param start start of output data.
- * \param offset requested start offset.
- * \param len requested number of bytes.
- * \param eof whether there is no more data to return.
- * \param data private data.
- * \return number of written bytes.
- *
- * No-op.
- */
-int drm_mem_info(char *buf, char **start, off_t offset,
-                int len, int *eof, void *data)
-{
-       return 0;
-}
-
-#if __OS_HAS_AGP
-static void *agp_remap(unsigned long offset, unsigned long size,
-                      struct drm_device * dev)
-{
-       unsigned long i, num_pages =
-           PAGE_ALIGN(size) / PAGE_SIZE;
-       struct drm_agp_mem *agpmem;
-       struct page **page_map;
-       struct page **phys_page_map;
-       void *addr;
-
-       size = PAGE_ALIGN(size);
-
-#ifdef __alpha__
-       offset -= dev->hose->mem_space->start;
-#endif
-
-       list_for_each_entry(agpmem, &dev->agp->memory, head)
-               if (agpmem->bound <= offset
-                   && (agpmem->bound + (agpmem->pages << PAGE_SHIFT)) >=
-                   (offset + size))
-                       break;
-       if (&agpmem->head == &dev->agp->memory)
-               return NULL;
-
-       /*
-        * OK, we're mapping AGP space on a chipset/platform on which memory accesses by
-        * the CPU do not get remapped by the GART.  We fix this by using the kernel's
-        * page-table instead (that's probably faster anyhow...).
-        */
-       /* note: use vmalloc() because num_pages could be large... */
-       page_map = vmalloc(num_pages * sizeof(struct page *));
-       if (!page_map)
-               return NULL;
-
-       phys_page_map = (agpmem->memory->pages + (offset - agpmem->bound) / PAGE_SIZE);
-       for (i = 0; i < num_pages; ++i)
-               page_map[i] = phys_page_map[i];
-       addr = vmap(page_map, num_pages, VM_IOREMAP, PAGE_AGP);
-       vfree(page_map);
-
-       return addr;
-}
-
-/** Wrapper around agp_free_memory() */
-void drm_free_agp(DRM_AGP_MEM * handle, int pages)
-{
-       agp_free_memory(handle);
-}
-EXPORT_SYMBOL(drm_free_agp);
-
-/** Wrapper around agp_bind_memory() */
-int drm_bind_agp(DRM_AGP_MEM * handle, unsigned int start)
-{
-       return agp_bind_memory(handle, start);
-}
-
-/** Wrapper around agp_unbind_memory() */
-int drm_unbind_agp(DRM_AGP_MEM * handle)
-{
-       return agp_unbind_memory(handle);
-}
-EXPORT_SYMBOL(drm_unbind_agp);
-
-#else  /*  __OS_HAS_AGP  */
-static inline void *agp_remap(unsigned long offset, unsigned long size,
-                             struct drm_device * dev)
-{
-       return NULL;
-}
-
-#endif                         /* agp */
-
-void drm_core_ioremap(struct drm_local_map *map, struct drm_device *dev)
-{
-       if (drm_core_has_AGP(dev) &&
-           dev->agp && dev->agp->cant_use_aperture && map->type == _DRM_AGP)
-               map->handle = agp_remap(map->offset, map->size, dev);
-       else
-               map->handle = ioremap(map->offset, map->size);
-}
-EXPORT_SYMBOL(drm_core_ioremap);
-
-void drm_core_ioremap_wc(struct drm_local_map *map, struct drm_device *dev)
-{
-       if (drm_core_has_AGP(dev) &&
-           dev->agp && dev->agp->cant_use_aperture && map->type == _DRM_AGP)
-               map->handle = agp_remap(map->offset, map->size, dev);
-       else
-               map->handle = ioremap_wc(map->offset, map->size);
-}
-EXPORT_SYMBOL(drm_core_ioremap_wc);
-
-void drm_core_ioremapfree(struct drm_local_map *map, struct drm_device *dev)
-{
-       if (!map->handle || !map->size)
-               return;
-
-       if (drm_core_has_AGP(dev) &&
-           dev->agp && dev->agp->cant_use_aperture && map->type == _DRM_AGP)
-               vunmap(map->handle);
-       else
-               iounmap(map->handle);
-}
-EXPORT_SYMBOL(drm_core_ioremapfree);
diff --git a/services4/3rdparty/linux_drm/drm_mm.c b/services4/3rdparty/linux_drm/drm_mm.c
deleted file mode 100644 (file)
index a6bfc30..0000000
+++ /dev/null
@@ -1,620 +0,0 @@
-/**************************************************************************
- *
- * Copyright 2006 Tungsten Graphics, Inc., Bismarck, ND., USA.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sub license, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice (including the
- * next paragraph) shall be included in all copies or substantial portions
- * of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
- * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
- * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
- * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
- * USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- *
- **************************************************************************/
-
-/*
- * Generic simple memory manager implementation. Intended to be used as a base
- * class implementation for more advanced memory managers.
- *
- * Note that the algorithm used is quite simple and there might be substantial
- * performance gains if a smarter free list is implemented. Currently it is just an
- * unordered stack of free regions. This could easily be improved if an RB-tree
- * is used instead. At least if we expect heavy fragmentation.
- *
- * Aligned allocations can also see improvement.
- *
- * Authors:
- * Thomas Hellström <thomas-at-tungstengraphics-dot-com>
- */
-
-#include "drmP.h"
-#include "drm_mm.h"
-#include <linux/slab.h>
-#include <linux/seq_file.h>
-
-#define MM_UNUSED_TARGET 4
-
-static struct drm_mm_node *drm_mm_kmalloc(struct drm_mm *mm, int atomic)
-{
-       struct drm_mm_node *child;
-
-       if (atomic)
-               child = kzalloc(sizeof(*child), GFP_ATOMIC);
-       else
-               child = kzalloc(sizeof(*child), GFP_KERNEL);
-
-       if (unlikely(child == NULL)) {
-               spin_lock(&mm->unused_lock);
-               if (list_empty(&mm->unused_nodes))
-                       child = NULL;
-               else {
-                       child =
-                           list_entry(mm->unused_nodes.next,
-                                      struct drm_mm_node, free_stack);
-                       list_del(&child->free_stack);
-                       --mm->num_unused;
-               }
-               spin_unlock(&mm->unused_lock);
-       }
-       return child;
-}
-
-/* drm_mm_pre_get() - pre allocate drm_mm_node structure
- * drm_mm:     memory manager struct we are pre-allocating for
- *
- * Returns 0 on success or -ENOMEM if allocation fails.
- */
-int drm_mm_pre_get(struct drm_mm *mm)
-{
-       struct drm_mm_node *node;
-
-       spin_lock(&mm->unused_lock);
-       while (mm->num_unused < MM_UNUSED_TARGET) {
-               spin_unlock(&mm->unused_lock);
-               node = kzalloc(sizeof(*node), GFP_KERNEL);
-               spin_lock(&mm->unused_lock);
-
-               if (unlikely(node == NULL)) {
-                       int ret = (mm->num_unused < 2) ? -ENOMEM : 0;
-                       spin_unlock(&mm->unused_lock);
-                       return ret;
-               }
-               ++mm->num_unused;
-               list_add_tail(&node->free_stack, &mm->unused_nodes);
-       }
-       spin_unlock(&mm->unused_lock);
-       return 0;
-}
-EXPORT_SYMBOL(drm_mm_pre_get);
-
-static int drm_mm_create_tail_node(struct drm_mm *mm,
-                                  unsigned long start,
-                                  unsigned long size, int atomic)
-{
-       struct drm_mm_node *child;
-
-       child = drm_mm_kmalloc(mm, atomic);
-       if (unlikely(child == NULL))
-               return -ENOMEM;
-
-       child->free = 1;
-       child->size = size;
-       child->start = start;
-       child->mm = mm;
-
-       list_add_tail(&child->node_list, &mm->node_list);
-       list_add_tail(&child->free_stack, &mm->free_stack);
-
-       return 0;
-}
-
-static struct drm_mm_node *drm_mm_split_at_start(struct drm_mm_node *parent,
-                                                unsigned long size,
-                                                int atomic)
-{
-       struct drm_mm_node *child;
-
-       child = drm_mm_kmalloc(parent->mm, atomic);
-       if (unlikely(child == NULL))
-               return NULL;
-
-       INIT_LIST_HEAD(&child->free_stack);
-
-       child->size = size;
-       child->start = parent->start;
-       child->mm = parent->mm;
-
-       list_add_tail(&child->node_list, &parent->node_list);
-       INIT_LIST_HEAD(&child->free_stack);
-
-       parent->size -= size;
-       parent->start += size;
-       return child;
-}
-
-
-struct drm_mm_node *drm_mm_get_block_generic(struct drm_mm_node *node,
-                                            unsigned long size,
-                                            unsigned alignment,
-                                            int atomic)
-{
-
-       struct drm_mm_node *align_splitoff = NULL;
-       unsigned tmp = 0;
-
-       if (alignment)
-               tmp = node->start % alignment;
-
-       if (tmp) {
-               align_splitoff =
-                   drm_mm_split_at_start(node, alignment - tmp, atomic);
-               if (unlikely(align_splitoff == NULL))
-                       return NULL;
-       }
-
-       if (node->size == size) {
-               list_del_init(&node->free_stack);
-               node->free = 0;
-       } else {
-               node = drm_mm_split_at_start(node, size, atomic);
-       }
-
-       if (align_splitoff)
-               drm_mm_put_block(align_splitoff);
-
-       return node;
-}
-EXPORT_SYMBOL(drm_mm_get_block_generic);
-
-struct drm_mm_node *drm_mm_get_block_range_generic(struct drm_mm_node *node,
-                                               unsigned long size,
-                                               unsigned alignment,
-                                               unsigned long start,
-                                               unsigned long end,
-                                               int atomic)
-{
-       struct drm_mm_node *align_splitoff = NULL;
-       unsigned tmp = 0;
-       unsigned wasted = 0;
-
-       if (node->start < start)
-               wasted += start - node->start;
-       if (alignment)
-               tmp = ((node->start + wasted) % alignment);
-
-       if (tmp)
-               wasted += alignment - tmp;
-       if (wasted) {
-               align_splitoff = drm_mm_split_at_start(node, wasted, atomic);
-               if (unlikely(align_splitoff == NULL))
-                       return NULL;
-       }
-
-       if (node->size == size) {
-               list_del_init(&node->free_stack);
-               node->free = 0;
-       } else {
-               node = drm_mm_split_at_start(node, size, atomic);
-       }
-
-       if (align_splitoff)
-               drm_mm_put_block(align_splitoff);
-
-       return node;
-}
-EXPORT_SYMBOL(drm_mm_get_block_range_generic);
-
-/*
- * Put a block. Merge with the previous and / or next block if they are free.
- * Otherwise add to the free stack.
- */
-
-void drm_mm_put_block(struct drm_mm_node *cur)
-{
-
-       struct drm_mm *mm = cur->mm;
-       struct list_head *cur_head = &cur->node_list;
-       struct list_head *root_head = &mm->node_list;
-       struct drm_mm_node *prev_node = NULL;
-       struct drm_mm_node *next_node;
-
-       int merged = 0;
-
-       BUG_ON(cur->scanned_block || cur->scanned_prev_free
-                                 || cur->scanned_next_free);
-
-       if (cur_head->prev != root_head) {
-               prev_node =
-                   list_entry(cur_head->prev, struct drm_mm_node, node_list);
-               if (prev_node->free) {
-                       prev_node->size += cur->size;
-                       merged = 1;
-               }
-       }
-       if (cur_head->next != root_head) {
-               next_node =
-                   list_entry(cur_head->next, struct drm_mm_node, node_list);
-               if (next_node->free) {
-                       if (merged) {
-                               prev_node->size += next_node->size;
-                               list_del(&next_node->node_list);
-                               list_del(&next_node->free_stack);
-                               spin_lock(&mm->unused_lock);
-                               if (mm->num_unused < MM_UNUSED_TARGET) {
-                                       list_add(&next_node->free_stack,
-                                                &mm->unused_nodes);
-                                       ++mm->num_unused;
-                               } else
-                                       kfree(next_node);
-                               spin_unlock(&mm->unused_lock);
-                       } else {
-                               next_node->size += cur->size;
-                               next_node->start = cur->start;
-                               merged = 1;
-                       }
-               }
-       }
-       if (!merged) {
-               cur->free = 1;
-               list_add(&cur->free_stack, &mm->free_stack);
-       } else {
-               list_del(&cur->node_list);
-               spin_lock(&mm->unused_lock);
-               if (mm->num_unused < MM_UNUSED_TARGET) {
-                       list_add(&cur->free_stack, &mm->unused_nodes);
-                       ++mm->num_unused;
-               } else
-                       kfree(cur);
-               spin_unlock(&mm->unused_lock);
-       }
-}
-
-EXPORT_SYMBOL(drm_mm_put_block);
-
-static int check_free_hole(unsigned long start, unsigned long end,
-                          unsigned long size, unsigned alignment)
-{
-       unsigned wasted = 0;
-
-       if (end - start < size)
-               return 0;
-
-       if (alignment) {
-               unsigned tmp = start % alignment;
-               if (tmp)
-                       wasted = alignment - tmp;
-       }
-
-       if (end >= start + size + wasted) {
-               return 1;
-       }
-
-       return 0;
-}
-
-struct drm_mm_node *drm_mm_search_free(const struct drm_mm *mm,
-                                      unsigned long size,
-                                      unsigned alignment, int best_match)
-{
-       struct drm_mm_node *entry;
-       struct drm_mm_node *best;
-       unsigned long best_size;
-
-       BUG_ON(mm->scanned_blocks);
-
-       best = NULL;
-       best_size = ~0UL;
-
-       list_for_each_entry(entry, &mm->free_stack, free_stack) {
-               if (!check_free_hole(entry->start, entry->start + entry->size,
-                                    size, alignment))
-                       continue;
-
-               if (!best_match)
-                       return entry;
-
-               if (entry->size < best_size) {
-                       best = entry;
-                       best_size = entry->size;
-               }
-       }
-
-       return best;
-}
-EXPORT_SYMBOL(drm_mm_search_free);
-
-struct drm_mm_node *drm_mm_search_free_in_range(const struct drm_mm *mm,
-                                               unsigned long size,
-                                               unsigned alignment,
-                                               unsigned long start,
-                                               unsigned long end,
-                                               int best_match)
-{
-       struct drm_mm_node *entry;
-       struct drm_mm_node *best;
-       unsigned long best_size;
-
-       BUG_ON(mm->scanned_blocks);
-
-       best = NULL;
-       best_size = ~0UL;
-
-       list_for_each_entry(entry, &mm->free_stack, free_stack) {
-               unsigned long adj_start = entry->start < start ?
-                       start : entry->start;
-               unsigned long adj_end = entry->start + entry->size > end ?
-                       end : entry->start + entry->size;
-
-               if (!check_free_hole(adj_start, adj_end, size, alignment))
-                       continue;
-
-               if (!best_match)
-                       return entry;
-
-               if (entry->size < best_size) {
-                       best = entry;
-                       best_size = entry->size;
-               }
-       }
-
-       return best;
-}
-EXPORT_SYMBOL(drm_mm_search_free_in_range);
-
-/**
- * Initializa lru scanning.
- *
- * This simply sets up the scanning routines with the parameters for the desired
- * hole.
- *
- * Warning: As long as the scan list is non-empty, no other operations than
- * adding/removing nodes to/from the scan list are allowed.
- */
-void drm_mm_init_scan(struct drm_mm *mm, unsigned long size,
-                     unsigned alignment)
-{
-       mm->scan_alignment = alignment;
-       mm->scan_size = size;
-       mm->scanned_blocks = 0;
-       mm->scan_hit_start = 0;
-       mm->scan_hit_size = 0;
-}
-EXPORT_SYMBOL(drm_mm_init_scan);
-
-/**
- * Add a node to the scan list that might be freed to make space for the desired
- * hole.
- *
- * Returns non-zero, if a hole has been found, zero otherwise.
- */
-int drm_mm_scan_add_block(struct drm_mm_node *node)
-{
-       struct drm_mm *mm = node->mm;
-       struct list_head *prev_free, *next_free;
-       struct drm_mm_node *prev_node, *next_node;
-
-       mm->scanned_blocks++;
-
-       prev_free = next_free = NULL;
-
-       BUG_ON(node->free);
-       node->scanned_block = 1;
-       node->free = 1;
-
-       if (node->node_list.prev != &mm->node_list) {
-               prev_node = list_entry(node->node_list.prev, struct drm_mm_node,
-                                      node_list);
-
-               if (prev_node->free) {
-                       list_del(&prev_node->node_list);
-
-                       node->start = prev_node->start;
-                       node->size += prev_node->size;
-
-                       prev_node->scanned_prev_free = 1;
-
-                       prev_free = &prev_node->free_stack;
-               }
-       }
-
-       if (node->node_list.next != &mm->node_list) {
-               next_node = list_entry(node->node_list.next, struct drm_mm_node,
-                                      node_list);
-
-               if (next_node->free) {
-                       list_del(&next_node->node_list);
-
-                       node->size += next_node->size;
-
-                       next_node->scanned_next_free = 1;
-
-                       next_free = &next_node->free_stack;
-               }
-       }
-
-       /* The free_stack list is not used for allocated objects, so these two
-        * pointers can be abused (as long as no allocations in this memory
-        * manager happens). */
-       node->free_stack.prev = prev_free;
-       node->free_stack.next = next_free;
-
-       if (check_free_hole(node->start, node->start + node->size,
-                           mm->scan_size, mm->scan_alignment)) {
-               mm->scan_hit_start = node->start;
-               mm->scan_hit_size = node->size;
-
-               return 1;
-       }
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_mm_scan_add_block);
-
-/**
- * Remove a node from the scan list.
- *
- * Nodes _must_ be removed in the exact same order from the scan list as they
- * have been added, otherwise the internal state of the memory manager will be
- * corrupted.
- *
- * When the scan list is empty, the selected memory nodes can be freed. An
- * immediatly following drm_mm_search_free with best_match = 0 will then return
- * the just freed block (because its at the top of the free_stack list).
- *
- * Returns one if this block should be evicted, zero otherwise. Will always
- * return zero when no hole has been found.
- */
-int drm_mm_scan_remove_block(struct drm_mm_node *node)
-{
-       struct drm_mm *mm = node->mm;
-       struct drm_mm_node *prev_node, *next_node;
-
-       mm->scanned_blocks--;
-
-       BUG_ON(!node->scanned_block);
-       node->scanned_block = 0;
-       node->free = 0;
-
-       prev_node = list_entry(node->free_stack.prev, struct drm_mm_node,
-                              free_stack);
-       next_node = list_entry(node->free_stack.next, struct drm_mm_node,
-                              free_stack);
-
-       if (prev_node) {
-               BUG_ON(!prev_node->scanned_prev_free);
-               prev_node->scanned_prev_free = 0;
-
-               list_add_tail(&prev_node->node_list, &node->node_list);
-
-               node->start = prev_node->start + prev_node->size;
-               node->size -= prev_node->size;
-       }
-
-       if (next_node) {
-               BUG_ON(!next_node->scanned_next_free);
-               next_node->scanned_next_free = 0;
-
-               list_add(&next_node->node_list, &node->node_list);
-
-               node->size -= next_node->size;
-       }
-
-       INIT_LIST_HEAD(&node->free_stack);
-
-       /* Only need to check for containement because start&size for the
-        * complete resulting free block (not just the desired part) is
-        * stored. */
-       if (node->start >= mm->scan_hit_start &&
-           node->start + node->size
-                       <= mm->scan_hit_start + mm->scan_hit_size) {
-               return 1;
-       }
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_mm_scan_remove_block);
-
-int drm_mm_clean(struct drm_mm * mm)
-{
-       struct list_head *head = &mm->node_list;
-
-       return (head->next->next == head);
-}
-EXPORT_SYMBOL(drm_mm_clean);
-
-int drm_mm_init(struct drm_mm * mm, unsigned long start, unsigned long size)
-{
-       INIT_LIST_HEAD(&mm->node_list);
-       INIT_LIST_HEAD(&mm->free_stack);
-       INIT_LIST_HEAD(&mm->unused_nodes);
-       mm->num_unused = 0;
-       mm->scanned_blocks = 0;
-       spin_lock_init(&mm->unused_lock);
-
-       return drm_mm_create_tail_node(mm, start, size, 0);
-}
-EXPORT_SYMBOL(drm_mm_init);
-
-void drm_mm_takedown(struct drm_mm * mm)
-{
-       struct list_head *bnode = mm->free_stack.next;
-       struct drm_mm_node *entry;
-       struct drm_mm_node *next;
-
-       entry = list_entry(bnode, struct drm_mm_node, free_stack);
-
-       if (entry->node_list.next != &mm->node_list ||
-           entry->free_stack.next != &mm->free_stack) {
-               DRM_ERROR("Memory manager not clean. Delaying takedown\n");
-               return;
-       }
-
-       list_del(&entry->free_stack);
-       list_del(&entry->node_list);
-       kfree(entry);
-
-       spin_lock(&mm->unused_lock);
-       list_for_each_entry_safe(entry, next, &mm->unused_nodes, free_stack) {
-               list_del(&entry->free_stack);
-               kfree(entry);
-               --mm->num_unused;
-       }
-       spin_unlock(&mm->unused_lock);
-
-       BUG_ON(mm->num_unused != 0);
-}
-EXPORT_SYMBOL(drm_mm_takedown);
-
-void drm_mm_debug_table(struct drm_mm *mm, const char *prefix)
-{
-       struct drm_mm_node *entry;
-       int total_used = 0, total_free = 0, total = 0;
-
-       list_for_each_entry(entry, &mm->node_list, node_list) {
-               printk(KERN_DEBUG "%s 0x%08lx-0x%08lx: %8ld: %s\n",
-                       prefix, entry->start, entry->start + entry->size,
-                       entry->size, entry->free ? "free" : "used");
-               total += entry->size;
-               if (entry->free)
-                       total_free += entry->size;
-               else
-                       total_used += entry->size;
-       }
-       printk(KERN_DEBUG "%s total: %d, used %d free %d\n", prefix, total,
-               total_used, total_free);
-}
-EXPORT_SYMBOL(drm_mm_debug_table);
-
-#if defined(CONFIG_DEBUG_FS)
-int drm_mm_dump_table(struct seq_file *m, struct drm_mm *mm)
-{
-       struct drm_mm_node *entry;
-       int total_used = 0, total_free = 0, total = 0;
-
-       list_for_each_entry(entry, &mm->node_list, node_list) {
-               seq_printf(m, "0x%08lx-0x%08lx: 0x%08lx: %s\n", entry->start, entry->start + entry->size, entry->size, entry->free ? "free" : "used");
-               total += entry->size;
-               if (entry->free)
-                       total_free += entry->size;
-               else
-                       total_used += entry->size;
-       }
-       seq_printf(m, "total: %d, used %d free %d\n", total, total_used, total_free);
-       return 0;
-}
-EXPORT_SYMBOL(drm_mm_dump_table);
-#endif
diff --git a/services4/3rdparty/linux_drm/drm_modes.c b/services4/3rdparty/linux_drm/drm_modes.c
deleted file mode 100644 (file)
index 58e65f9..0000000
+++ /dev/null
@@ -1,976 +0,0 @@
-/*
- * Copyright Â© 1997-2003 by The XFree86 Project, Inc.
- * Copyright Â© 2007 Dave Airlie
- * Copyright Â© 2007-2008 Intel Corporation
- *   Jesse Barnes <jesse.barnes@intel.com>
- * Copyright 2005-2006 Luc Verhaegen
- * Copyright (c) 2001, Andy Ritger  aritger@nvidia.com
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- *
- * Except as contained in this notice, the name of the copyright holder(s)
- * and author(s) shall not be used in advertising or otherwise to promote
- * the sale, use or other dealings in this Software without prior written
- * authorization from the copyright holder(s) and author(s).
- */
-
-#include <linux/list.h>
-#include <linux/list_sort.h>
-#include "drmP.h"
-#include "drm.h"
-#include "drm_crtc.h"
-
-/**
- * drm_mode_debug_printmodeline - debug print a mode
- * @dev: DRM device
- * @mode: mode to print
- *
- * LOCKING:
- * None.
- *
- * Describe @mode using DRM_DEBUG.
- */
-void drm_mode_debug_printmodeline(struct drm_display_mode *mode)
-{
-       DRM_DEBUG_KMS("Modeline %d:\"%s\" %d %d %d %d %d %d %d %d %d %d "
-                       "0x%x 0x%x\n",
-               mode->base.id, mode->name, mode->vrefresh, mode->clock,
-               mode->hdisplay, mode->hsync_start,
-               mode->hsync_end, mode->htotal,
-               mode->vdisplay, mode->vsync_start,
-               mode->vsync_end, mode->vtotal, mode->type, mode->flags);
-}
-EXPORT_SYMBOL(drm_mode_debug_printmodeline);
-
-/**
- * drm_cvt_mode -create a modeline based on CVT algorithm
- * @dev: DRM device
- * @hdisplay: hdisplay size
- * @vdisplay: vdisplay size
- * @vrefresh  : vrefresh rate
- * @reduced : Whether the GTF calculation is simplified
- * @interlaced:Whether the interlace is supported
- *
- * LOCKING:
- * none.
- *
- * return the modeline based on CVT algorithm
- *
- * This function is called to generate the modeline based on CVT algorithm
- * according to the hdisplay, vdisplay, vrefresh.
- * It is based from the VESA(TM) Coordinated Video Timing Generator by
- * Graham Loveridge April 9, 2003 available at
- * http://www.elo.utfsm.cl/~elo212/docs/CVTd6r1.xls 
- *
- * And it is copied from xf86CVTmode in xserver/hw/xfree86/modes/xf86cvt.c.
- * What I have done is to translate it by using integer calculation.
- */
-#define HV_FACTOR                      1000
-struct drm_display_mode *drm_cvt_mode(struct drm_device *dev, int hdisplay,
-                                     int vdisplay, int vrefresh,
-                                     bool reduced, bool interlaced, bool margins)
-{
-       /* 1) top/bottom margin size (% of height) - default: 1.8, */
-#define        CVT_MARGIN_PERCENTAGE           18
-       /* 2) character cell horizontal granularity (pixels) - default 8 */
-#define        CVT_H_GRANULARITY               8
-       /* 3) Minimum vertical porch (lines) - default 3 */
-#define        CVT_MIN_V_PORCH                 3
-       /* 4) Minimum number of vertical back porch lines - default 6 */
-#define        CVT_MIN_V_BPORCH                6
-       /* Pixel Clock step (kHz) */
-#define CVT_CLOCK_STEP                 250
-       struct drm_display_mode *drm_mode;
-       unsigned int vfieldrate, hperiod;
-       int hdisplay_rnd, hmargin, vdisplay_rnd, vmargin, vsync;
-       int interlace;
-
-       /* allocate the drm_display_mode structure. If failure, we will
-        * return directly
-        */
-       drm_mode = drm_mode_create(dev);
-       if (!drm_mode)
-               return NULL;
-
-       /* the CVT default refresh rate is 60Hz */
-       if (!vrefresh)
-               vrefresh = 60;
-
-       /* the required field fresh rate */
-       if (interlaced)
-               vfieldrate = vrefresh * 2;
-       else
-               vfieldrate = vrefresh;
-
-       /* horizontal pixels */
-       hdisplay_rnd = hdisplay - (hdisplay % CVT_H_GRANULARITY);
-
-       /* determine the left&right borders */
-       hmargin = 0;
-       if (margins) {
-               hmargin = hdisplay_rnd * CVT_MARGIN_PERCENTAGE / 1000;
-               hmargin -= hmargin % CVT_H_GRANULARITY;
-       }
-       /* find the total active pixels */
-       drm_mode->hdisplay = hdisplay_rnd + 2 * hmargin;
-
-       /* find the number of lines per field */
-       if (interlaced)
-               vdisplay_rnd = vdisplay / 2;
-       else
-               vdisplay_rnd = vdisplay;
-
-       /* find the top & bottom borders */
-       vmargin = 0;
-       if (margins)
-               vmargin = vdisplay_rnd * CVT_MARGIN_PERCENTAGE / 1000;
-
-       drm_mode->vdisplay = vdisplay + 2 * vmargin;
-
-       /* Interlaced */
-       if (interlaced)
-               interlace = 1;
-       else
-               interlace = 0;
-
-       /* Determine VSync Width from aspect ratio */
-       if (!(vdisplay % 3) && ((vdisplay * 4 / 3) == hdisplay))
-               vsync = 4;
-       else if (!(vdisplay % 9) && ((vdisplay * 16 / 9) == hdisplay))
-               vsync = 5;
-       else if (!(vdisplay % 10) && ((vdisplay * 16 / 10) == hdisplay))
-               vsync = 6;
-       else if (!(vdisplay % 4) && ((vdisplay * 5 / 4) == hdisplay))
-               vsync = 7;
-       else if (!(vdisplay % 9) && ((vdisplay * 15 / 9) == hdisplay))
-               vsync = 7;
-       else /* custom */
-               vsync = 10;
-
-       if (!reduced) {
-               /* simplify the GTF calculation */
-               /* 4) Minimum time of vertical sync + back porch interval (µs)
-                * default 550.0
-                */
-               int tmp1, tmp2;
-#define CVT_MIN_VSYNC_BP       550
-               /* 3) Nominal HSync width (% of line period) - default 8 */
-#define CVT_HSYNC_PERCENTAGE   8
-               unsigned int hblank_percentage;
-               int vsyncandback_porch, vback_porch, hblank;
-
-               /* estimated the horizontal period */
-               tmp1 = HV_FACTOR * 1000000  -
-                               CVT_MIN_VSYNC_BP * HV_FACTOR * vfieldrate;
-               tmp2 = (vdisplay_rnd + 2 * vmargin + CVT_MIN_V_PORCH) * 2 +
-                               interlace;
-               hperiod = tmp1 * 2 / (tmp2 * vfieldrate);
-
-               tmp1 = CVT_MIN_VSYNC_BP * HV_FACTOR / hperiod + 1;
-               /* 9. Find number of lines in sync + backporch */
-               if (tmp1 < (vsync + CVT_MIN_V_PORCH))
-                       vsyncandback_porch = vsync + CVT_MIN_V_PORCH;
-               else
-                       vsyncandback_porch = tmp1;
-               /* 10. Find number of lines in back porch */
-               vback_porch = vsyncandback_porch - vsync;
-               drm_mode->vtotal = vdisplay_rnd + 2 * vmargin +
-                               vsyncandback_porch + CVT_MIN_V_PORCH;
-               /* 5) Definition of Horizontal blanking time limitation */
-               /* Gradient (%/kHz) - default 600 */
-#define CVT_M_FACTOR   600
-               /* Offset (%) - default 40 */
-#define CVT_C_FACTOR   40
-               /* Blanking time scaling factor - default 128 */
-#define CVT_K_FACTOR   128
-               /* Scaling factor weighting - default 20 */
-#define CVT_J_FACTOR   20
-#define CVT_M_PRIME    (CVT_M_FACTOR * CVT_K_FACTOR / 256)
-#define CVT_C_PRIME    ((CVT_C_FACTOR - CVT_J_FACTOR) * CVT_K_FACTOR / 256 + \
-                        CVT_J_FACTOR)
-               /* 12. Find ideal blanking duty cycle from formula */
-               hblank_percentage = CVT_C_PRIME * HV_FACTOR - CVT_M_PRIME *
-                                       hperiod / 1000;
-               /* 13. Blanking time */
-               if (hblank_percentage < 20 * HV_FACTOR)
-                       hblank_percentage = 20 * HV_FACTOR;
-               hblank = drm_mode->hdisplay * hblank_percentage /
-                        (100 * HV_FACTOR - hblank_percentage);
-               hblank -= hblank % (2 * CVT_H_GRANULARITY);
-               /* 14. find the total pixes per line */
-               drm_mode->htotal = drm_mode->hdisplay + hblank;
-               drm_mode->hsync_end = drm_mode->hdisplay + hblank / 2;
-               drm_mode->hsync_start = drm_mode->hsync_end -
-                       (drm_mode->htotal * CVT_HSYNC_PERCENTAGE) / 100;
-               drm_mode->hsync_start += CVT_H_GRANULARITY -
-                       drm_mode->hsync_start % CVT_H_GRANULARITY;
-               /* fill the Vsync values */
-               drm_mode->vsync_start = drm_mode->vdisplay + CVT_MIN_V_PORCH;
-               drm_mode->vsync_end = drm_mode->vsync_start + vsync;
-       } else {
-               /* Reduced blanking */
-               /* Minimum vertical blanking interval time (µs)- default 460 */
-#define CVT_RB_MIN_VBLANK      460
-               /* Fixed number of clocks for horizontal sync */
-#define CVT_RB_H_SYNC          32
-               /* Fixed number of clocks for horizontal blanking */
-#define CVT_RB_H_BLANK         160
-               /* Fixed number of lines for vertical front porch - default 3*/
-#define CVT_RB_VFPORCH         3
-               int vbilines;
-               int tmp1, tmp2;
-               /* 8. Estimate Horizontal period. */
-               tmp1 = HV_FACTOR * 1000000 -
-                       CVT_RB_MIN_VBLANK * HV_FACTOR * vfieldrate;
-               tmp2 = vdisplay_rnd + 2 * vmargin;
-               hperiod = tmp1 / (tmp2 * vfieldrate);
-               /* 9. Find number of lines in vertical blanking */
-               vbilines = CVT_RB_MIN_VBLANK * HV_FACTOR / hperiod + 1;
-               /* 10. Check if vertical blanking is sufficient */
-               if (vbilines < (CVT_RB_VFPORCH + vsync + CVT_MIN_V_BPORCH))
-                       vbilines = CVT_RB_VFPORCH + vsync + CVT_MIN_V_BPORCH;
-               /* 11. Find total number of lines in vertical field */
-               drm_mode->vtotal = vdisplay_rnd + 2 * vmargin + vbilines;
-               /* 12. Find total number of pixels in a line */
-               drm_mode->htotal = drm_mode->hdisplay + CVT_RB_H_BLANK;
-               /* Fill in HSync values */
-               drm_mode->hsync_end = drm_mode->hdisplay + CVT_RB_H_BLANK / 2;
-               drm_mode->hsync_start = drm_mode->hsync_end - CVT_RB_H_SYNC;
-               /* Fill in VSync values */
-               drm_mode->vsync_start = drm_mode->vdisplay + CVT_RB_VFPORCH;
-               drm_mode->vsync_end = drm_mode->vsync_start + vsync;
-       }
-       /* 15/13. Find pixel clock frequency (kHz for xf86) */
-       drm_mode->clock = drm_mode->htotal * HV_FACTOR * 1000 / hperiod;
-       drm_mode->clock -= drm_mode->clock % CVT_CLOCK_STEP;
-       /* 18/16. Find actual vertical frame frequency */
-       /* ignore - just set the mode flag for interlaced */
-       if (interlaced) {
-               drm_mode->vtotal *= 2;
-               drm_mode->flags |= DRM_MODE_FLAG_INTERLACE;
-       }
-       /* Fill the mode line name */
-       drm_mode_set_name(drm_mode);
-       if (reduced)
-               drm_mode->flags |= (DRM_MODE_FLAG_PHSYNC |
-                                       DRM_MODE_FLAG_NVSYNC);
-       else
-               drm_mode->flags |= (DRM_MODE_FLAG_PVSYNC |
-                                       DRM_MODE_FLAG_NHSYNC);
-
-       return drm_mode;
-}
-EXPORT_SYMBOL(drm_cvt_mode);
-
-/**
- * drm_gtf_mode_complex - create the modeline based on full GTF algorithm
- *
- * @dev                :drm device
- * @hdisplay   :hdisplay size
- * @vdisplay   :vdisplay size
- * @vrefresh   :vrefresh rate.
- * @interlaced :whether the interlace is supported
- * @margins    :desired margin size
- * @GTF_[MCKJ]  :extended GTF formula parameters
- *
- * LOCKING.
- * none.
- *
- * return the modeline based on full GTF algorithm.
- *
- * GTF feature blocks specify C and J in multiples of 0.5, so we pass them
- * in here multiplied by two.  For a C of 40, pass in 80.
- */
-struct drm_display_mode *
-drm_gtf_mode_complex(struct drm_device *dev, int hdisplay, int vdisplay,
-                    int vrefresh, bool interlaced, int margins,
-                    int GTF_M, int GTF_2C, int GTF_K, int GTF_2J)
-{      /* 1) top/bottom margin size (% of height) - default: 1.8, */
-#define        GTF_MARGIN_PERCENTAGE           18
-       /* 2) character cell horizontal granularity (pixels) - default 8 */
-#define        GTF_CELL_GRAN                   8
-       /* 3) Minimum vertical porch (lines) - default 3 */
-#define        GTF_MIN_V_PORCH                 1
-       /* width of vsync in lines */
-#define V_SYNC_RQD                     3
-       /* width of hsync as % of total line */
-#define H_SYNC_PERCENT                 8
-       /* min time of vsync + back porch (microsec) */
-#define MIN_VSYNC_PLUS_BP              550
-       /* C' and M' are part of the Blanking Duty Cycle computation */
-#define GTF_C_PRIME    ((((GTF_2C - GTF_2J) * GTF_K / 256) + GTF_2J) / 2)
-#define GTF_M_PRIME    (GTF_K * GTF_M / 256)
-       struct drm_display_mode *drm_mode;
-       unsigned int hdisplay_rnd, vdisplay_rnd, vfieldrate_rqd;
-       int top_margin, bottom_margin;
-       int interlace;
-       unsigned int hfreq_est;
-       int vsync_plus_bp, vback_porch;
-       unsigned int vtotal_lines, vfieldrate_est, hperiod;
-       unsigned int vfield_rate, vframe_rate;
-       int left_margin, right_margin;
-       unsigned int total_active_pixels, ideal_duty_cycle;
-       unsigned int hblank, total_pixels, pixel_freq;
-       int hsync, hfront_porch, vodd_front_porch_lines;
-       unsigned int tmp1, tmp2;
-
-       drm_mode = drm_mode_create(dev);
-       if (!drm_mode)
-               return NULL;
-
-       /* 1. In order to give correct results, the number of horizontal
-        * pixels requested is first processed to ensure that it is divisible
-        * by the character size, by rounding it to the nearest character
-        * cell boundary:
-        */
-       hdisplay_rnd = (hdisplay + GTF_CELL_GRAN / 2) / GTF_CELL_GRAN;
-       hdisplay_rnd = hdisplay_rnd * GTF_CELL_GRAN;
-
-       /* 2. If interlace is requested, the number of vertical lines assumed
-        * by the calculation must be halved, as the computation calculates
-        * the number of vertical lines per field.
-        */
-       if (interlaced)
-               vdisplay_rnd = vdisplay / 2;
-       else
-               vdisplay_rnd = vdisplay;
-
-       /* 3. Find the frame rate required: */
-       if (interlaced)
-               vfieldrate_rqd = vrefresh * 2;
-       else
-               vfieldrate_rqd = vrefresh;
-
-       /* 4. Find number of lines in Top margin: */
-       top_margin = 0;
-       if (margins)
-               top_margin = (vdisplay_rnd * GTF_MARGIN_PERCENTAGE + 500) /
-                               1000;
-       /* 5. Find number of lines in bottom margin: */
-       bottom_margin = top_margin;
-
-       /* 6. If interlace is required, then set variable interlace: */
-       if (interlaced)
-               interlace = 1;
-       else
-               interlace = 0;
-
-       /* 7. Estimate the Horizontal frequency */
-       {
-               tmp1 = (1000000  - MIN_VSYNC_PLUS_BP * vfieldrate_rqd) / 500;
-               tmp2 = (vdisplay_rnd + 2 * top_margin + GTF_MIN_V_PORCH) *
-                               2 + interlace;
-               hfreq_est = (tmp2 * 1000 * vfieldrate_rqd) / tmp1;
-       }
-
-       /* 8. Find the number of lines in V sync + back porch */
-       /* [V SYNC+BP] = RINT(([MIN VSYNC+BP] * hfreq_est / 1000000)) */
-       vsync_plus_bp = MIN_VSYNC_PLUS_BP * hfreq_est / 1000;
-       vsync_plus_bp = (vsync_plus_bp + 500) / 1000;
-       /*  9. Find the number of lines in V back porch alone: */
-       vback_porch = vsync_plus_bp - V_SYNC_RQD;
-       /*  10. Find the total number of lines in Vertical field period: */
-       vtotal_lines = vdisplay_rnd + top_margin + bottom_margin +
-                       vsync_plus_bp + GTF_MIN_V_PORCH;
-       /*  11. Estimate the Vertical field frequency: */
-       vfieldrate_est = hfreq_est / vtotal_lines;
-       /*  12. Find the actual horizontal period: */
-       hperiod = 1000000 / (vfieldrate_rqd * vtotal_lines);
-
-       /*  13. Find the actual Vertical field frequency: */
-       vfield_rate = hfreq_est / vtotal_lines;
-       /*  14. Find the Vertical frame frequency: */
-       if (interlaced)
-               vframe_rate = vfield_rate / 2;
-       else
-               vframe_rate = vfield_rate;
-       /*  15. Find number of pixels in left margin: */
-       if (margins)
-               left_margin = (hdisplay_rnd * GTF_MARGIN_PERCENTAGE + 500) /
-                               1000;
-       else
-               left_margin = 0;
-
-       /* 16.Find number of pixels in right margin: */
-       right_margin = left_margin;
-       /* 17.Find total number of active pixels in image and left and right */
-       total_active_pixels = hdisplay_rnd + left_margin + right_margin;
-       /* 18.Find the ideal blanking duty cycle from blanking duty cycle */
-       ideal_duty_cycle = GTF_C_PRIME * 1000 -
-                               (GTF_M_PRIME * 1000000 / hfreq_est);
-       /* 19.Find the number of pixels in the blanking time to the nearest
-        * double character cell: */
-       hblank = total_active_pixels * ideal_duty_cycle /
-                       (100000 - ideal_duty_cycle);
-       hblank = (hblank + GTF_CELL_GRAN) / (2 * GTF_CELL_GRAN);
-       hblank = hblank * 2 * GTF_CELL_GRAN;
-       /* 20.Find total number of pixels: */
-       total_pixels = total_active_pixels + hblank;
-       /* 21.Find pixel clock frequency: */
-       pixel_freq = total_pixels * hfreq_est / 1000;
-       /* Stage 1 computations are now complete; I should really pass
-        * the results to another function and do the Stage 2 computations,
-        * but I only need a few more values so I'll just append the
-        * computations here for now */
-       /* 17. Find the number of pixels in the horizontal sync period: */
-       hsync = H_SYNC_PERCENT * total_pixels / 100;
-       hsync = (hsync + GTF_CELL_GRAN / 2) / GTF_CELL_GRAN;
-       hsync = hsync * GTF_CELL_GRAN;
-       /* 18. Find the number of pixels in horizontal front porch period */
-       hfront_porch = hblank / 2 - hsync;
-       /*  36. Find the number of lines in the odd front porch period: */
-       vodd_front_porch_lines = GTF_MIN_V_PORCH ;
-
-       /* finally, pack the results in the mode struct */
-       drm_mode->hdisplay = hdisplay_rnd;
-       drm_mode->hsync_start = hdisplay_rnd + hfront_porch;
-       drm_mode->hsync_end = drm_mode->hsync_start + hsync;
-       drm_mode->htotal = total_pixels;
-       drm_mode->vdisplay = vdisplay_rnd;
-       drm_mode->vsync_start = vdisplay_rnd + vodd_front_porch_lines;
-       drm_mode->vsync_end = drm_mode->vsync_start + V_SYNC_RQD;
-       drm_mode->vtotal = vtotal_lines;
-
-       drm_mode->clock = pixel_freq;
-
-       if (interlaced) {
-               drm_mode->vtotal *= 2;
-               drm_mode->flags |= DRM_MODE_FLAG_INTERLACE;
-       }
-
-       drm_mode_set_name(drm_mode);
-       if (GTF_M == 600 && GTF_2C == 80 && GTF_K == 128 && GTF_2J == 40)
-               drm_mode->flags = DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC;
-       else
-               drm_mode->flags = DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NVSYNC;
-
-       return drm_mode;
-}
-EXPORT_SYMBOL(drm_gtf_mode_complex);
-
-/**
- * drm_gtf_mode - create the modeline based on GTF algorithm
- *
- * @dev                :drm device
- * @hdisplay   :hdisplay size
- * @vdisplay   :vdisplay size
- * @vrefresh   :vrefresh rate.
- * @interlaced :whether the interlace is supported
- * @margins    :whether the margin is supported
- *
- * LOCKING.
- * none.
- *
- * return the modeline based on GTF algorithm
- *
- * This function is to create the modeline based on the GTF algorithm.
- * Generalized Timing Formula is derived from:
- *     GTF Spreadsheet by Andy Morrish (1/5/97)
- *     available at http://www.vesa.org
- *
- * And it is copied from the file of xserver/hw/xfree86/modes/xf86gtf.c.
- * What I have done is to translate it by using integer calculation.
- * I also refer to the function of fb_get_mode in the file of
- * drivers/video/fbmon.c
- *
- * Standard GTF parameters:
- * M = 600
- * C = 40
- * K = 128
- * J = 20
- */
-struct drm_display_mode *
-drm_gtf_mode(struct drm_device *dev, int hdisplay, int vdisplay, int vrefresh,
-            bool lace, int margins)
-{
-       return drm_gtf_mode_complex(dev, hdisplay, vdisplay, vrefresh, lace,
-                                   margins, 600, 40 * 2, 128, 20 * 2);
-}
-EXPORT_SYMBOL(drm_gtf_mode);
-
-/**
- * drm_mode_set_name - set the name on a mode
- * @mode: name will be set in this mode
- *
- * LOCKING:
- * None.
- *
- * Set the name of @mode to a standard format.
- */
-void drm_mode_set_name(struct drm_display_mode *mode)
-{
-       bool interlaced = !!(mode->flags & DRM_MODE_FLAG_INTERLACE);
-
-       snprintf(mode->name, DRM_DISPLAY_MODE_LEN, "%dx%d%s",
-                mode->hdisplay, mode->vdisplay,
-                interlaced ? "i" : "");
-}
-EXPORT_SYMBOL(drm_mode_set_name);
-
-/**
- * drm_mode_list_concat - move modes from one list to another
- * @head: source list
- * @new: dst list
- *
- * LOCKING:
- * Caller must ensure both lists are locked.
- *
- * Move all the modes from @head to @new.
- */
-void drm_mode_list_concat(struct list_head *head, struct list_head *new)
-{
-
-       struct list_head *entry, *tmp;
-
-       list_for_each_safe(entry, tmp, head) {
-               list_move_tail(entry, new);
-       }
-}
-EXPORT_SYMBOL(drm_mode_list_concat);
-
-/**
- * drm_mode_width - get the width of a mode
- * @mode: mode
- *
- * LOCKING:
- * None.
- *
- * Return @mode's width (hdisplay) value.
- *
- * FIXME: is this needed?
- *
- * RETURNS:
- * @mode->hdisplay
- */
-int drm_mode_width(struct drm_display_mode *mode)
-{
-       return mode->hdisplay;
-
-}
-EXPORT_SYMBOL(drm_mode_width);
-
-/**
- * drm_mode_height - get the height of a mode
- * @mode: mode
- *
- * LOCKING:
- * None.
- *
- * Return @mode's height (vdisplay) value.
- *
- * FIXME: is this needed?
- *
- * RETURNS:
- * @mode->vdisplay
- */
-int drm_mode_height(struct drm_display_mode *mode)
-{
-       return mode->vdisplay;
-}
-EXPORT_SYMBOL(drm_mode_height);
-
-/** drm_mode_hsync - get the hsync of a mode
- * @mode: mode
- *
- * LOCKING:
- * None.
- *
- * Return @modes's hsync rate in kHz, rounded to the nearest int.
- */
-int drm_mode_hsync(struct drm_display_mode *mode)
-{
-       unsigned int calc_val;
-
-       if (mode->hsync)
-               return mode->hsync;
-
-       if (mode->htotal < 0)
-               return 0;
-
-       calc_val = (mode->clock * 1000) / mode->htotal; /* hsync in Hz */
-       calc_val += 500;                                /* round to 1000Hz */
-       calc_val /= 1000;                               /* truncate to kHz */
-
-       return calc_val;
-}
-EXPORT_SYMBOL(drm_mode_hsync);
-
-/**
- * drm_mode_vrefresh - get the vrefresh of a mode
- * @mode: mode
- *
- * LOCKING:
- * None.
- *
- * Return @mode's vrefresh rate in Hz or calculate it if necessary.
- *
- * FIXME: why is this needed?  shouldn't vrefresh be set already?
- *
- * RETURNS:
- * Vertical refresh rate. It will be the result of actual value plus 0.5.
- * If it is 70.288, it will return 70Hz.
- * If it is 59.6, it will return 60Hz.
- */
-int drm_mode_vrefresh(struct drm_display_mode *mode)
-{
-       int refresh = 0;
-       unsigned int calc_val;
-
-       if (mode->vrefresh > 0)
-               refresh = mode->vrefresh;
-       else if (mode->htotal > 0 && mode->vtotal > 0) {
-               int vtotal;
-               vtotal = mode->vtotal;
-               /* work out vrefresh the value will be x1000 */
-               calc_val = (mode->clock * 1000);
-               calc_val /= mode->htotal;
-               refresh = (calc_val + vtotal / 2) / vtotal;
-
-               if (mode->flags & DRM_MODE_FLAG_INTERLACE)
-                       refresh *= 2;
-               if (mode->flags & DRM_MODE_FLAG_DBLSCAN)
-                       refresh /= 2;
-               if (mode->vscan > 1)
-                       refresh /= mode->vscan;
-       }
-       return refresh;
-}
-EXPORT_SYMBOL(drm_mode_vrefresh);
-
-/**
- * drm_mode_set_crtcinfo - set CRTC modesetting parameters
- * @p: mode
- * @adjust_flags: unused? (FIXME)
- *
- * LOCKING:
- * None.
- *
- * Setup the CRTC modesetting parameters for @p, adjusting if necessary.
- */
-void drm_mode_set_crtcinfo(struct drm_display_mode *p, int adjust_flags)
-{
-       if ((p == NULL) || ((p->type & DRM_MODE_TYPE_CRTC_C) == DRM_MODE_TYPE_BUILTIN))
-               return;
-
-       p->crtc_hdisplay = p->hdisplay;
-       p->crtc_hsync_start = p->hsync_start;
-       p->crtc_hsync_end = p->hsync_end;
-       p->crtc_htotal = p->htotal;
-       p->crtc_hskew = p->hskew;
-       p->crtc_vdisplay = p->vdisplay;
-       p->crtc_vsync_start = p->vsync_start;
-       p->crtc_vsync_end = p->vsync_end;
-       p->crtc_vtotal = p->vtotal;
-
-       if (p->flags & DRM_MODE_FLAG_INTERLACE) {
-               if (adjust_flags & CRTC_INTERLACE_HALVE_V) {
-                       p->crtc_vdisplay /= 2;
-                       p->crtc_vsync_start /= 2;
-                       p->crtc_vsync_end /= 2;
-                       p->crtc_vtotal /= 2;
-               }
-
-               p->crtc_vtotal |= 1;
-       }
-
-       if (p->flags & DRM_MODE_FLAG_DBLSCAN) {
-               p->crtc_vdisplay *= 2;
-               p->crtc_vsync_start *= 2;
-               p->crtc_vsync_end *= 2;
-               p->crtc_vtotal *= 2;
-       }
-
-       if (p->vscan > 1) {
-               p->crtc_vdisplay *= p->vscan;
-               p->crtc_vsync_start *= p->vscan;
-               p->crtc_vsync_end *= p->vscan;
-               p->crtc_vtotal *= p->vscan;
-       }
-
-       p->crtc_vblank_start = min(p->crtc_vsync_start, p->crtc_vdisplay);
-       p->crtc_vblank_end = max(p->crtc_vsync_end, p->crtc_vtotal);
-       p->crtc_hblank_start = min(p->crtc_hsync_start, p->crtc_hdisplay);
-       p->crtc_hblank_end = max(p->crtc_hsync_end, p->crtc_htotal);
-
-       p->crtc_hadjusted = false;
-       p->crtc_vadjusted = false;
-}
-EXPORT_SYMBOL(drm_mode_set_crtcinfo);
-
-
-/**
- * drm_mode_duplicate - allocate and duplicate an existing mode
- * @m: mode to duplicate
- *
- * LOCKING:
- * None.
- *
- * Just allocate a new mode, copy the existing mode into it, and return
- * a pointer to it.  Used to create new instances of established modes.
- */
-struct drm_display_mode *drm_mode_duplicate(struct drm_device *dev,
-                                           struct drm_display_mode *mode)
-{
-       struct drm_display_mode *nmode;
-       int new_id;
-
-       nmode = drm_mode_create(dev);
-       if (!nmode)
-               return NULL;
-
-       new_id = nmode->base.id;
-       *nmode = *mode;
-       nmode->base.id = new_id;
-       INIT_LIST_HEAD(&nmode->head);
-       return nmode;
-}
-EXPORT_SYMBOL(drm_mode_duplicate);
-
-/**
- * drm_mode_equal - test modes for equality
- * @mode1: first mode
- * @mode2: second mode
- *
- * LOCKING:
- * None.
- *
- * Check to see if @mode1 and @mode2 are equivalent.
- *
- * RETURNS:
- * True if the modes are equal, false otherwise.
- */
-bool drm_mode_equal(struct drm_display_mode *mode1, struct drm_display_mode *mode2)
-{
-       /* do clock check convert to PICOS so fb modes get matched
-        * the same */
-       if (mode1->clock && mode2->clock) {
-               if (KHZ2PICOS(mode1->clock) != KHZ2PICOS(mode2->clock))
-                       return false;
-       } else if (mode1->clock != mode2->clock)
-               return false;
-
-       if (mode1->hdisplay == mode2->hdisplay &&
-           mode1->hsync_start == mode2->hsync_start &&
-           mode1->hsync_end == mode2->hsync_end &&
-           mode1->htotal == mode2->htotal &&
-           mode1->hskew == mode2->hskew &&
-           mode1->vdisplay == mode2->vdisplay &&
-           mode1->vsync_start == mode2->vsync_start &&
-           mode1->vsync_end == mode2->vsync_end &&
-           mode1->vtotal == mode2->vtotal &&
-           mode1->vscan == mode2->vscan &&
-           mode1->flags == mode2->flags)
-               return true;
-
-       return false;
-}
-EXPORT_SYMBOL(drm_mode_equal);
-
-/**
- * drm_mode_validate_size - make sure modes adhere to size constraints
- * @dev: DRM device
- * @mode_list: list of modes to check
- * @maxX: maximum width
- * @maxY: maximum height
- * @maxPitch: max pitch
- *
- * LOCKING:
- * Caller must hold a lock protecting @mode_list.
- *
- * The DRM device (@dev) has size and pitch limits.  Here we validate the
- * modes we probed for @dev against those limits and set their status as
- * necessary.
- */
-void drm_mode_validate_size(struct drm_device *dev,
-                           struct list_head *mode_list,
-                           int maxX, int maxY, int maxPitch)
-{
-       struct drm_display_mode *mode;
-
-       list_for_each_entry(mode, mode_list, head) {
-               if (maxPitch > 0 && mode->hdisplay > maxPitch)
-                       mode->status = MODE_BAD_WIDTH;
-
-               if (maxX > 0 && mode->hdisplay > maxX)
-                       mode->status = MODE_VIRTUAL_X;
-
-               if (maxY > 0 && mode->vdisplay > maxY)
-                       mode->status = MODE_VIRTUAL_Y;
-       }
-}
-EXPORT_SYMBOL(drm_mode_validate_size);
-
-/**
- * drm_mode_validate_clocks - validate modes against clock limits
- * @dev: DRM device
- * @mode_list: list of modes to check
- * @min: minimum clock rate array
- * @max: maximum clock rate array
- * @n_ranges: number of clock ranges (size of arrays)
- *
- * LOCKING:
- * Caller must hold a lock protecting @mode_list.
- *
- * Some code may need to check a mode list against the clock limits of the
- * device in question.  This function walks the mode list, testing to make
- * sure each mode falls within a given range (defined by @min and @max
- * arrays) and sets @mode->status as needed.
- */
-void drm_mode_validate_clocks(struct drm_device *dev,
-                             struct list_head *mode_list,
-                             int *min, int *max, int n_ranges)
-{
-       struct drm_display_mode *mode;
-       int i;
-
-       list_for_each_entry(mode, mode_list, head) {
-               bool good = false;
-               for (i = 0; i < n_ranges; i++) {
-                       if (mode->clock >= min[i] && mode->clock <= max[i]) {
-                               good = true;
-                               break;
-                       }
-               }
-               if (!good)
-                       mode->status = MODE_CLOCK_RANGE;
-       }
-}
-EXPORT_SYMBOL(drm_mode_validate_clocks);
-
-/**
- * drm_mode_prune_invalid - remove invalid modes from mode list
- * @dev: DRM device
- * @mode_list: list of modes to check
- * @verbose: be verbose about it
- *
- * LOCKING:
- * Caller must hold a lock protecting @mode_list.
- *
- * Once mode list generation is complete, a caller can use this routine to
- * remove invalid modes from a mode list.  If any of the modes have a
- * status other than %MODE_OK, they are removed from @mode_list and freed.
- */
-void drm_mode_prune_invalid(struct drm_device *dev,
-                           struct list_head *mode_list, bool verbose)
-{
-       struct drm_display_mode *mode, *t;
-
-       list_for_each_entry_safe(mode, t, mode_list, head) {
-               if (mode->status != MODE_OK) {
-                       list_del(&mode->head);
-                       if (verbose) {
-                               drm_mode_debug_printmodeline(mode);
-                               DRM_DEBUG_KMS("Not using %s mode %d\n",
-                                       mode->name, mode->status);
-                       }
-                       drm_mode_destroy(dev, mode);
-               }
-       }
-}
-EXPORT_SYMBOL(drm_mode_prune_invalid);
-
-/**
- * drm_mode_compare - compare modes for favorability
- * @priv: unused
- * @lh_a: list_head for first mode
- * @lh_b: list_head for second mode
- *
- * LOCKING:
- * None.
- *
- * Compare two modes, given by @lh_a and @lh_b, returning a value indicating
- * which is better.
- *
- * RETURNS:
- * Negative if @lh_a is better than @lh_b, zero if they're equivalent, or
- * positive if @lh_b is better than @lh_a.
- */
-static int drm_mode_compare(void *priv, struct list_head *lh_a, struct list_head *lh_b)
-{
-       struct drm_display_mode *a = list_entry(lh_a, struct drm_display_mode, head);
-       struct drm_display_mode *b = list_entry(lh_b, struct drm_display_mode, head);
-       int diff;
-
-       diff = ((b->type & DRM_MODE_TYPE_PREFERRED) != 0) -
-               ((a->type & DRM_MODE_TYPE_PREFERRED) != 0);
-       if (diff)
-               return diff;
-       diff = b->hdisplay * b->vdisplay - a->hdisplay * a->vdisplay;
-       if (diff)
-               return diff;
-       diff = b->clock - a->clock;
-       return diff;
-}
-
-/**
- * drm_mode_sort - sort mode list
- * @mode_list: list to sort
- *
- * LOCKING:
- * Caller must hold a lock protecting @mode_list.
- *
- * Sort @mode_list by favorability, putting good modes first.
- */
-void drm_mode_sort(struct list_head *mode_list)
-{
-       list_sort(NULL, mode_list, drm_mode_compare);
-}
-EXPORT_SYMBOL(drm_mode_sort);
-
-/**
- * drm_mode_connector_list_update - update the mode list for the connector
- * @connector: the connector to update
- *
- * LOCKING:
- * Caller must hold a lock protecting @mode_list.
- *
- * This moves the modes from the @connector probed_modes list
- * to the actual mode list. It compares the probed mode against the current
- * list and only adds different modes. All modes unverified after this point
- * will be removed by the prune invalid modes.
- */
-void drm_mode_connector_list_update(struct drm_connector *connector)
-{
-       struct drm_display_mode *mode;
-       struct drm_display_mode *pmode, *pt;
-       int found_it;
-
-       list_for_each_entry_safe(pmode, pt, &connector->probed_modes,
-                                head) {
-               found_it = 0;
-               /* go through current modes checking for the new probed mode */
-               list_for_each_entry(mode, &connector->modes, head) {
-                       if (drm_mode_equal(pmode, mode)) {
-                               found_it = 1;
-                               /* if equal delete the probed mode */
-                               mode->status = pmode->status;
-                               /* Merge type bits together */
-                               mode->type |= pmode->type;
-                               list_del(&pmode->head);
-                               drm_mode_destroy(connector->dev, pmode);
-                               break;
-                       }
-               }
-
-               if (!found_it) {
-                       list_move_tail(&pmode->head, &connector->modes);
-               }
-       }
-}
-EXPORT_SYMBOL(drm_mode_connector_list_update);
diff --git a/services4/3rdparty/linux_drm/drm_pci.c b/services4/3rdparty/linux_drm/drm_pci.c
deleted file mode 100644 (file)
index f5bd9e5..0000000
+++ /dev/null
@@ -1,274 +0,0 @@
-/* drm_pci.h -- PCI DMA memory management wrappers for DRM -*- linux-c -*- */
-/**
- * \file drm_pci.c
- * \brief Functions and ioctls to manage PCI memory
- *
- * \warning These interfaces aren't stable yet.
- *
- * \todo Implement the remaining ioctl's for the PCI pools.
- * \todo The wrappers here are so thin that they would be better off inlined..
- *
- * \author José Fonseca <jrfonseca@tungstengraphics.com>
- * \author Leif Delgass <ldelgass@retinalburn.net>
- */
-
-/*
- * Copyright 2003 José Fonseca.
- * Copyright 2003 Leif Delgass.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
- * AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
- * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/pci.h>
-#include <linux/slab.h>
-#include <linux/dma-mapping.h>
-#include "drmP.h"
-
-/**********************************************************************/
-/** \name PCI memory */
-/*@{*/
-
-/**
- * \brief Allocate a PCI consistent memory block, for DMA.
- */
-drm_dma_handle_t *drm_pci_alloc(struct drm_device * dev, size_t size, size_t align)
-{
-       drm_dma_handle_t *dmah;
-#if 1
-       unsigned long addr;
-       size_t sz;
-#endif
-
-       /* pci_alloc_consistent only guarantees alignment to the smallest
-        * PAGE_SIZE order which is greater than or equal to the requested size.
-        * Return NULL here for now to make sure nobody tries for larger alignment
-        */
-       if (align > size)
-               return NULL;
-
-       dmah = kmalloc(sizeof(drm_dma_handle_t), GFP_KERNEL);
-       if (!dmah)
-               return NULL;
-
-       dmah->size = size;
-       dmah->vaddr = dma_alloc_coherent(&dev->pdev->dev, size, &dmah->busaddr, GFP_KERNEL | __GFP_COMP);
-
-       if (dmah->vaddr == NULL) {
-               kfree(dmah);
-               return NULL;
-       }
-
-       memset(dmah->vaddr, 0, size);
-
-       /* XXX - Is virt_to_page() legal for consistent mem? */
-       /* Reserve */
-       for (addr = (unsigned long)dmah->vaddr, sz = size;
-            sz > 0; addr += PAGE_SIZE, sz -= PAGE_SIZE) {
-               SetPageReserved(virt_to_page(addr));
-       }
-
-       return dmah;
-}
-
-EXPORT_SYMBOL(drm_pci_alloc);
-
-/**
- * \brief Free a PCI consistent memory block without freeing its descriptor.
- *
- * This function is for internal use in the Linux-specific DRM core code.
- */
-void __drm_pci_free(struct drm_device * dev, drm_dma_handle_t * dmah)
-{
-#if 1
-       unsigned long addr;
-       size_t sz;
-#endif
-
-       if (dmah->vaddr) {
-               /* XXX - Is virt_to_page() legal for consistent mem? */
-               /* Unreserve */
-               for (addr = (unsigned long)dmah->vaddr, sz = dmah->size;
-                    sz > 0; addr += PAGE_SIZE, sz -= PAGE_SIZE) {
-                       ClearPageReserved(virt_to_page(addr));
-               }
-               dma_free_coherent(&dev->pdev->dev, dmah->size, dmah->vaddr,
-                                 dmah->busaddr);
-       }
-}
-
-/**
- * \brief Free a PCI consistent memory block
- */
-void drm_pci_free(struct drm_device * dev, drm_dma_handle_t * dmah)
-{
-       __drm_pci_free(dev, dmah);
-       kfree(dmah);
-}
-
-EXPORT_SYMBOL(drm_pci_free);
-
-#ifdef CONFIG_PCI
-/**
- * Register.
- *
- * \param pdev - PCI device structure
- * \param ent entry from the PCI ID table with device type flags
- * \return zero on success or a negative number on failure.
- *
- * Attempt to gets inter module "drm" information. If we are first
- * then register the character device and inter module information.
- * Try and register, if we fail to register, backout previous work.
- */
-int drm_get_pci_dev(struct pci_dev *pdev, const struct pci_device_id *ent,
-                   struct drm_driver *driver)
-{
-       struct drm_device *dev;
-       int ret;
-
-       DRM_DEBUG("\n");
-
-       dev = kzalloc(sizeof(*dev), GFP_KERNEL);
-       if (!dev)
-               return -ENOMEM;
-
-       ret = pci_enable_device(pdev);
-       if (ret)
-               goto err_g1;
-
-       pci_set_master(pdev);
-
-       dev->pdev = pdev;
-       dev->dev = &pdev->dev;
-
-       dev->pci_device = pdev->device;
-       dev->pci_vendor = pdev->vendor;
-
-#ifdef __alpha__
-       dev->hose = pdev->sysdata;
-#endif
-
-       mutex_lock(&drm_global_mutex);
-
-       if ((ret = drm_fill_in_dev(dev, ent, driver))) {
-               printk(KERN_ERR "DRM: Fill_in_dev failed.\n");
-               goto err_g2;
-       }
-
-       if (drm_core_check_feature(dev, DRIVER_MODESET)) {
-               pci_set_drvdata(pdev, dev);
-               ret = drm_get_minor(dev, &dev->control, DRM_MINOR_CONTROL);
-               if (ret)
-                       goto err_g2;
-       }
-
-       if ((ret = drm_get_minor(dev, &dev->primary, DRM_MINOR_LEGACY)))
-               goto err_g3;
-
-       if (dev->driver->load) {
-               ret = dev->driver->load(dev, ent->driver_data);
-               if (ret)
-                       goto err_g4;
-       }
-
-       /* setup the grouping for the legacy output */
-       if (drm_core_check_feature(dev, DRIVER_MODESET)) {
-               ret = drm_mode_group_init_legacy_group(dev,
-                                               &dev->primary->mode_group);
-               if (ret)
-                       goto err_g4;
-       }
-
-       list_add_tail(&dev->driver_item, &driver->device_list);
-
-       DRM_INFO("Initialized %s %d.%d.%d %s for %s on minor %d\n",
-                driver->name, driver->major, driver->minor, driver->patchlevel,
-                driver->date, pci_name(pdev), dev->primary->index);
-
-       mutex_unlock(&drm_global_mutex);
-       return 0;
-
-err_g4:
-       drm_put_minor(&dev->primary);
-err_g3:
-       if (drm_core_check_feature(dev, DRIVER_MODESET))
-               drm_put_minor(&dev->control);
-err_g2:
-       pci_disable_device(pdev);
-err_g1:
-       kfree(dev);
-       mutex_unlock(&drm_global_mutex);
-       return ret;
-}
-EXPORT_SYMBOL(drm_get_pci_dev);
-
-/**
- * PCI device initialization. Called via drm_init at module load time,
- *
- * \return zero on success or a negative number on failure.
- *
- * Initializes a drm_device structures,registering the
- * stubs and initializing the AGP device.
- *
- * Expands the \c DRIVER_PREINIT and \c DRIVER_POST_INIT macros before and
- * after the initialization for driver customization.
- */
-int drm_pci_init(struct drm_driver *driver)
-{
-       struct pci_dev *pdev = NULL;
-       const struct pci_device_id *pid;
-       int i;
-
-       if (driver->driver_features & DRIVER_MODESET)
-               return pci_register_driver(&driver->pci_driver);
-
-       /* If not using KMS, fall back to stealth mode manual scanning. */
-       for (i = 0; driver->pci_driver.id_table[i].vendor != 0; i++) {
-               pid = &driver->pci_driver.id_table[i];
-
-               /* Loop around setting up a DRM device for each PCI device
-                * matching our ID and device class.  If we had the internal
-                * function that pci_get_subsys and pci_get_class used, we'd
-                * be able to just pass pid in instead of doing a two-stage
-                * thing.
-                */
-               pdev = NULL;
-               while ((pdev =
-                       pci_get_subsys(pid->vendor, pid->device, pid->subvendor,
-                                      pid->subdevice, pdev)) != NULL) {
-                       if ((pdev->class & pid->class_mask) != pid->class)
-                               continue;
-
-                       /* stealth mode requires a manual probe */
-                       pci_dev_get(pdev);
-                       drm_get_pci_dev(pdev, pid, driver);
-               }
-       }
-       return 0;
-}
-
-#else
-
-int drm_pci_init(struct drm_driver *driver)
-{
-       return -1;
-}
-
-#endif
-/*@}*/
diff --git a/services4/3rdparty/linux_drm/drm_platform.c b/services4/3rdparty/linux_drm/drm_platform.c
deleted file mode 100644 (file)
index 92d1d0f..0000000
+++ /dev/null
@@ -1,127 +0,0 @@
-/*
- * Derived from drm_pci.c
- *
- * Copyright 2003 José Fonseca.
- * Copyright 2003 Leif Delgass.
- * Copyright (c) 2009, Code Aurora Forum.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
- * AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
- * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-
-/**
- * Register.
- *
- * \param platdev - Platform device struture
- * \return zero on success or a negative number on failure.
- *
- * Attempt to gets inter module "drm" information. If we are first
- * then register the character device and inter module information.
- * Try and register, if we fail to register, backout previous work.
- */
-
-int drm_get_platform_dev(struct platform_device *platdev,
-                        struct drm_driver *driver)
-{
-       struct drm_device *dev;
-       int ret;
-
-       DRM_DEBUG("\n");
-
-       dev = kzalloc(sizeof(*dev), GFP_KERNEL);
-       if (!dev)
-               return -ENOMEM;
-
-       dev->platformdev = platdev;
-       dev->dev = &platdev->dev;
-
-       mutex_lock(&drm_global_mutex);
-
-       ret = drm_fill_in_dev(dev, NULL, driver);
-
-       if (ret) {
-               printk(KERN_ERR "DRM: Fill_in_dev failed.\n");
-               goto err_g1;
-       }
-
-       if (drm_core_check_feature(dev, DRIVER_MODESET)) {
-               dev_set_drvdata(&platdev->dev, dev);
-               ret = drm_get_minor(dev, &dev->control, DRM_MINOR_CONTROL);
-               if (ret)
-                       goto err_g1;
-       }
-
-       ret = drm_get_minor(dev, &dev->primary, DRM_MINOR_LEGACY);
-       if (ret)
-               goto err_g2;
-
-       if (dev->driver->load) {
-               ret = dev->driver->load(dev, 0);
-               if (ret)
-                       goto err_g3;
-       }
-
-       /* setup the grouping for the legacy output */
-       if (drm_core_check_feature(dev, DRIVER_MODESET)) {
-               ret = drm_mode_group_init_legacy_group(dev,
-                               &dev->primary->mode_group);
-               if (ret)
-                       goto err_g3;
-       }
-
-       list_add_tail(&dev->driver_item, &driver->device_list);
-
-       mutex_unlock(&drm_global_mutex);
-
-       DRM_INFO("Initialized %s %d.%d.%d %s on minor %d\n",
-                driver->name, driver->major, driver->minor, driver->patchlevel,
-                driver->date, dev->primary->index);
-
-       return 0;
-
-err_g3:
-       drm_put_minor(&dev->primary);
-err_g2:
-       if (drm_core_check_feature(dev, DRIVER_MODESET))
-               drm_put_minor(&dev->control);
-err_g1:
-       kfree(dev);
-       mutex_unlock(&drm_global_mutex);
-       return ret;
-}
-EXPORT_SYMBOL(drm_get_platform_dev);
-
-/**
- * Platform device initialization. Called via drm_init at module load time,
- *
- * \return zero on success or a negative number on failure.
- *
- * Initializes a drm_device structures,registering the
- * stubs
- *
- * Expands the \c DRIVER_PREINIT and \c DRIVER_POST_INIT macros before and
- * after the initialization for driver customization.
- */
-
-int drm_platform_init(struct drm_driver *driver)
-{
-       return drm_get_platform_dev(driver->platform_device, driver);
-}
diff --git a/services4/3rdparty/linux_drm/drm_proc.c b/services4/3rdparty/linux_drm/drm_proc.c
deleted file mode 100644 (file)
index 9e5b07e..0000000
+++ /dev/null
@@ -1,221 +0,0 @@
-/**
- * \file drm_proc.c
- * /proc support for DRM
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- *
- * \par Acknowledgements:
- *    Matthew J Sottek <matthew.j.sottek@intel.com> sent in a patch to fix
- *    the problem with the proc files not outputting all their information.
- */
-
-/*
- * Created: Mon Jan 11 09:48:47 1999 by faith@valinux.com
- *
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/seq_file.h>
-#include <linux/slab.h>
-#include "drmP.h"
-
-/***************************************************
- * Initialization, etc.
- **************************************************/
-
-/**
- * Proc file list.
- */
-static struct drm_info_list drm_proc_list[] = {
-       {"name", drm_name_info, 0},
-       {"vm", drm_vm_info, 0},
-       {"clients", drm_clients_info, 0},
-       {"queues", drm_queues_info, 0},
-       {"bufs", drm_bufs_info, 0},
-       {"gem_names", drm_gem_name_info, DRIVER_GEM},
-#if DRM_DEBUG_CODE
-       {"vma", drm_vma_info, 0},
-#endif
-};
-#define DRM_PROC_ENTRIES ARRAY_SIZE(drm_proc_list)
-
-static int drm_proc_open(struct inode *inode, struct file *file)
-{
-       struct drm_info_node* node = PDE(inode)->data;
-
-       return single_open(file, node->info_ent->show, node);
-}
-
-static const struct file_operations drm_proc_fops = {
-       .owner = THIS_MODULE,
-       .open = drm_proc_open,
-       .read = seq_read,
-       .llseek = seq_lseek,
-       .release = single_release,
-};
-
-
-/**
- * Initialize a given set of proc files for a device
- *
- * \param files The array of files to create
- * \param count The number of files given
- * \param root DRI proc dir entry.
- * \param minor device minor number
- * \return Zero on success, non-zero on failure
- *
- * Create a given set of proc files represented by an array of
- * gdm_proc_lists in the given root directory.
- */
-int drm_proc_create_files(struct drm_info_list *files, int count,
-                         struct proc_dir_entry *root, struct drm_minor *minor)
-{
-       struct drm_device *dev = minor->dev;
-       struct proc_dir_entry *ent;
-       struct drm_info_node *tmp;
-       char name[64];
-       int i, ret;
-
-       for (i = 0; i < count; i++) {
-               u32 features = files[i].driver_features;
-
-               if (features != 0 &&
-                   (dev->driver->driver_features & features) != features)
-                       continue;
-
-               tmp = kmalloc(sizeof(struct drm_info_node), GFP_KERNEL);
-               if (tmp == NULL) {
-                       ret = -1;
-                       goto fail;
-               }
-               tmp->minor = minor;
-               tmp->info_ent = &files[i];
-               list_add(&tmp->list, &minor->proc_nodes.list);
-
-               ent = proc_create_data(files[i].name, S_IRUGO, root,
-                                      &drm_proc_fops, tmp);
-               if (!ent) {
-                       DRM_ERROR("Cannot create /proc/dri/%s/%s\n",
-                                 name, files[i].name);
-                       list_del(&tmp->list);
-                       kfree(tmp);
-                       ret = -1;
-                       goto fail;
-               }
-
-       }
-       return 0;
-
-fail:
-       for (i = 0; i < count; i++)
-               remove_proc_entry(drm_proc_list[i].name, minor->proc_root);
-       return ret;
-}
-
-/**
- * Initialize the DRI proc filesystem for a device
- *
- * \param dev DRM device
- * \param minor device minor number
- * \param root DRI proc dir entry.
- * \param dev_root resulting DRI device proc dir entry.
- * \return root entry pointer on success, or NULL on failure.
- *
- * Create the DRI proc root entry "/proc/dri", the device proc root entry
- * "/proc/dri/%minor%/", and each entry in proc_list as
- * "/proc/dri/%minor%/%name%".
- */
-int drm_proc_init(struct drm_minor *minor, int minor_id,
-                 struct proc_dir_entry *root)
-{
-       char name[64];
-       int ret;
-
-       INIT_LIST_HEAD(&minor->proc_nodes.list);
-       sprintf(name, "%d", minor_id);
-       minor->proc_root = proc_mkdir(name, root);
-       if (!minor->proc_root) {
-               DRM_ERROR("Cannot create /proc/dri/%s\n", name);
-               return -1;
-       }
-
-       ret = drm_proc_create_files(drm_proc_list, DRM_PROC_ENTRIES,
-                                   minor->proc_root, minor);
-       if (ret) {
-               remove_proc_entry(name, root);
-               minor->proc_root = NULL;
-               DRM_ERROR("Failed to create core drm proc files\n");
-               return ret;
-       }
-
-       return 0;
-}
-
-int drm_proc_remove_files(struct drm_info_list *files, int count,
-                         struct drm_minor *minor)
-{
-       struct list_head *pos, *q;
-       struct drm_info_node *tmp;
-       int i;
-
-       for (i = 0; i < count; i++) {
-               list_for_each_safe(pos, q, &minor->proc_nodes.list) {
-                       tmp = list_entry(pos, struct drm_info_node, list);
-                       if (tmp->info_ent == &files[i]) {
-                               remove_proc_entry(files[i].name,
-                                                 minor->proc_root);
-                               list_del(pos);
-                               kfree(tmp);
-                       }
-               }
-       }
-       return 0;
-}
-
-/**
- * Cleanup the proc filesystem resources.
- *
- * \param minor device minor number.
- * \param root DRI proc dir entry.
- * \param dev_root DRI device proc dir entry.
- * \return always zero.
- *
- * Remove all proc entries created by proc_init().
- */
-int drm_proc_cleanup(struct drm_minor *minor, struct proc_dir_entry *root)
-{
-       char name[64];
-
-       if (!root || !minor->proc_root)
-               return 0;
-
-       drm_proc_remove_files(drm_proc_list, DRM_PROC_ENTRIES, minor);
-
-       sprintf(name, "%d", minor->index);
-       remove_proc_entry(name, root);
-
-       return 0;
-}
-
diff --git a/services4/3rdparty/linux_drm/drm_scatter.c b/services4/3rdparty/linux_drm/drm_scatter.c
deleted file mode 100644 (file)
index d15e09b..0000000
+++ /dev/null
@@ -1,217 +0,0 @@
-/**
- * \file drm_scatter.c
- * IOCTLs to manage scatter/gather memory
- *
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Mon Dec 18 23:20:54 2000 by gareth@valinux.com
- *
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/vmalloc.h>
-#include <linux/slab.h>
-#include "drmP.h"
-
-#define DEBUG_SCATTER 0
-
-static inline void *drm_vmalloc_dma(unsigned long size)
-{
-#if defined(__powerpc__) && defined(CONFIG_NOT_COHERENT_CACHE)
-       return __vmalloc(size, GFP_KERNEL, PAGE_KERNEL | _PAGE_NO_CACHE);
-#else
-       return vmalloc_32(size);
-#endif
-}
-
-void drm_sg_cleanup(struct drm_sg_mem * entry)
-{
-       struct page *page;
-       int i;
-
-       for (i = 0; i < entry->pages; i++) {
-               page = entry->pagelist[i];
-               if (page)
-                       ClearPageReserved(page);
-       }
-
-       vfree(entry->virtual);
-
-       kfree(entry->busaddr);
-       kfree(entry->pagelist);
-       kfree(entry);
-}
-
-#ifdef _LP64
-# define ScatterHandle(x) (unsigned int)((x >> 32) + (x & ((1L << 32) - 1)))
-#else
-# define ScatterHandle(x) (unsigned int)(x)
-#endif
-
-int drm_sg_alloc(struct drm_device *dev, struct drm_scatter_gather * request)
-{
-       struct drm_sg_mem *entry;
-       unsigned long pages, i, j;
-
-       DRM_DEBUG("\n");
-
-       if (!drm_core_check_feature(dev, DRIVER_SG))
-               return -EINVAL;
-
-       if (dev->sg)
-               return -EINVAL;
-
-       entry = kmalloc(sizeof(*entry), GFP_KERNEL);
-       if (!entry)
-               return -ENOMEM;
-
-       memset(entry, 0, sizeof(*entry));
-       pages = (request->size + PAGE_SIZE - 1) / PAGE_SIZE;
-       DRM_DEBUG("size=%ld pages=%ld\n", request->size, pages);
-
-       entry->pages = pages;
-       entry->pagelist = kmalloc(pages * sizeof(*entry->pagelist), GFP_KERNEL);
-       if (!entry->pagelist) {
-               kfree(entry);
-               return -ENOMEM;
-       }
-
-       memset(entry->pagelist, 0, pages * sizeof(*entry->pagelist));
-
-       entry->busaddr = kmalloc(pages * sizeof(*entry->busaddr), GFP_KERNEL);
-       if (!entry->busaddr) {
-               kfree(entry->pagelist);
-               kfree(entry);
-               return -ENOMEM;
-       }
-       memset((void *)entry->busaddr, 0, pages * sizeof(*entry->busaddr));
-
-       entry->virtual = drm_vmalloc_dma(pages << PAGE_SHIFT);
-       if (!entry->virtual) {
-               kfree(entry->busaddr);
-               kfree(entry->pagelist);
-               kfree(entry);
-               return -ENOMEM;
-       }
-
-       /* This also forces the mapping of COW pages, so our page list
-        * will be valid.  Please don't remove it...
-        */
-       memset(entry->virtual, 0, pages << PAGE_SHIFT);
-
-       entry->handle = ScatterHandle((unsigned long)entry->virtual);
-
-       DRM_DEBUG("handle  = %08lx\n", entry->handle);
-       DRM_DEBUG("virtual = %p\n", entry->virtual);
-
-       for (i = (unsigned long)entry->virtual, j = 0; j < pages;
-            i += PAGE_SIZE, j++) {
-               entry->pagelist[j] = vmalloc_to_page((void *)i);
-               if (!entry->pagelist[j])
-                       goto failed;
-               SetPageReserved(entry->pagelist[j]);
-       }
-
-       request->handle = entry->handle;
-
-       dev->sg = entry;
-
-#if DEBUG_SCATTER
-       /* Verify that each page points to its virtual address, and vice
-        * versa.
-        */
-       {
-               int error = 0;
-
-               for (i = 0; i < pages; i++) {
-                       unsigned long *tmp;
-
-                       tmp = page_address(entry->pagelist[i]);
-                       for (j = 0;
-                            j < PAGE_SIZE / sizeof(unsigned long);
-                            j++, tmp++) {
-                               *tmp = 0xcafebabe;
-                       }
-                       tmp = (unsigned long *)((u8 *) entry->virtual +
-                                               (PAGE_SIZE * i));
-                       for (j = 0;
-                            j < PAGE_SIZE / sizeof(unsigned long);
-                            j++, tmp++) {
-                               if (*tmp != 0xcafebabe && error == 0) {
-                                       error = 1;
-                                       DRM_ERROR("Scatter allocation error, "
-                                                 "pagelist does not match "
-                                                 "virtual mapping\n");
-                               }
-                       }
-                       tmp = page_address(entry->pagelist[i]);
-                       for (j = 0;
-                            j < PAGE_SIZE / sizeof(unsigned long);
-                            j++, tmp++) {
-                               *tmp = 0;
-                       }
-               }
-               if (error == 0)
-                       DRM_ERROR("Scatter allocation matches pagelist\n");
-       }
-#endif
-
-       return 0;
-
-      failed:
-       drm_sg_cleanup(entry);
-       return -ENOMEM;
-}
-
-int drm_sg_alloc_ioctl(struct drm_device *dev, void *data,
-                      struct drm_file *file_priv)
-{
-       struct drm_scatter_gather *request = data;
-
-       return drm_sg_alloc(dev, request);
-
-}
-
-int drm_sg_free(struct drm_device *dev, void *data,
-               struct drm_file *file_priv)
-{
-       struct drm_scatter_gather *request = data;
-       struct drm_sg_mem *entry;
-
-       if (!drm_core_check_feature(dev, DRIVER_SG))
-               return -EINVAL;
-
-       entry = dev->sg;
-       dev->sg = NULL;
-
-       if (!entry || entry->handle != request->handle)
-               return -EINVAL;
-
-       DRM_DEBUG("virtual  = %p\n", entry->virtual);
-
-       drm_sg_cleanup(entry);
-
-       return 0;
-}
diff --git a/services4/3rdparty/linux_drm/drm_sman.c b/services4/3rdparty/linux_drm/drm_sman.c
deleted file mode 100644 (file)
index 463aed9..0000000
+++ /dev/null
@@ -1,352 +0,0 @@
-/**************************************************************************
- *
- * Copyright 2006 Tungsten Graphics, Inc., Bismarck., ND., USA.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sub license, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
- * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
- * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
- * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
- * USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- * The above copyright notice and this permission notice (including the
- * next paragraph) shall be included in all copies or substantial portions
- * of the Software.
- *
- *
- **************************************************************************/
-/*
- * Simple memory manager interface that keeps track on allocate regions on a
- * per "owner" basis. All regions associated with an "owner" can be released
- * with a simple call. Typically if the "owner" exists. The owner is any
- * "unsigned long" identifier. Can typically be a pointer to a file private
- * struct or a context identifier.
- *
- * Authors:
- * Thomas Hellström <thomas-at-tungstengraphics-dot-com>
- */
-
-#include "drm_sman.h"
-
-struct drm_owner_item {
-       struct drm_hash_item owner_hash;
-       struct list_head sman_list;
-       struct list_head mem_blocks;
-};
-
-void drm_sman_takedown(struct drm_sman * sman)
-{
-       drm_ht_remove(&sman->user_hash_tab);
-       drm_ht_remove(&sman->owner_hash_tab);
-       kfree(sman->mm);
-}
-
-EXPORT_SYMBOL(drm_sman_takedown);
-
-int
-drm_sman_init(struct drm_sman * sman, unsigned int num_managers,
-             unsigned int user_order, unsigned int owner_order)
-{
-       int ret = 0;
-
-       sman->mm = (struct drm_sman_mm *) kcalloc(num_managers,
-                                                 sizeof(*sman->mm),
-                                                 GFP_KERNEL);
-       if (!sman->mm) {
-               ret = -ENOMEM;
-               goto out;
-       }
-       sman->num_managers = num_managers;
-       INIT_LIST_HEAD(&sman->owner_items);
-       ret = drm_ht_create(&sman->owner_hash_tab, owner_order);
-       if (ret)
-               goto out1;
-       ret = drm_ht_create(&sman->user_hash_tab, user_order);
-       if (!ret)
-               goto out;
-
-       drm_ht_remove(&sman->owner_hash_tab);
-out1:
-       kfree(sman->mm);
-out:
-       return ret;
-}
-
-EXPORT_SYMBOL(drm_sman_init);
-
-static void *drm_sman_mm_allocate(void *private, unsigned long size,
-                                 unsigned alignment)
-{
-       struct drm_mm *mm = (struct drm_mm *) private;
-       struct drm_mm_node *tmp;
-
-       tmp = drm_mm_search_free(mm, size, alignment, 1);
-       if (!tmp) {
-               return NULL;
-       }
-       tmp = drm_mm_get_block(tmp, size, alignment);
-       return tmp;
-}
-
-static void drm_sman_mm_free(void *private, void *ref)
-{
-       struct drm_mm_node *node = (struct drm_mm_node *) ref;
-
-       drm_mm_put_block(node);
-}
-
-static void drm_sman_mm_destroy(void *private)
-{
-       struct drm_mm *mm = (struct drm_mm *) private;
-       drm_mm_takedown(mm);
-       kfree(mm);
-}
-
-static unsigned long drm_sman_mm_offset(void *private, void *ref)
-{
-       struct drm_mm_node *node = (struct drm_mm_node *) ref;
-       return node->start;
-}
-
-int
-drm_sman_set_range(struct drm_sman * sman, unsigned int manager,
-                  unsigned long start, unsigned long size)
-{
-       struct drm_sman_mm *sman_mm;
-       struct drm_mm *mm;
-       int ret;
-
-       BUG_ON(manager >= sman->num_managers);
-
-       sman_mm = &sman->mm[manager];
-       mm = kzalloc(sizeof(*mm), GFP_KERNEL);
-       if (!mm) {
-               return -ENOMEM;
-       }
-       sman_mm->private = mm;
-       ret = drm_mm_init(mm, start, size);
-
-       if (ret) {
-               kfree(mm);
-               return ret;
-       }
-
-       sman_mm->allocate = drm_sman_mm_allocate;
-       sman_mm->free = drm_sman_mm_free;
-       sman_mm->destroy = drm_sman_mm_destroy;
-       sman_mm->offset = drm_sman_mm_offset;
-
-       return 0;
-}
-
-EXPORT_SYMBOL(drm_sman_set_range);
-
-int
-drm_sman_set_manager(struct drm_sman * sman, unsigned int manager,
-                    struct drm_sman_mm * allocator)
-{
-       BUG_ON(manager >= sman->num_managers);
-       sman->mm[manager] = *allocator;
-
-       return 0;
-}
-EXPORT_SYMBOL(drm_sman_set_manager);
-
-static struct drm_owner_item *drm_sman_get_owner_item(struct drm_sman * sman,
-                                                unsigned long owner)
-{
-       int ret;
-       struct drm_hash_item *owner_hash_item;
-       struct drm_owner_item *owner_item;
-
-       ret = drm_ht_find_item(&sman->owner_hash_tab, owner, &owner_hash_item);
-       if (!ret) {
-               return drm_hash_entry(owner_hash_item, struct drm_owner_item,
-                                     owner_hash);
-       }
-
-       owner_item = kzalloc(sizeof(*owner_item), GFP_KERNEL);
-       if (!owner_item)
-               goto out;
-
-       INIT_LIST_HEAD(&owner_item->mem_blocks);
-       owner_item->owner_hash.key = owner;
-       if (drm_ht_insert_item(&sman->owner_hash_tab, &owner_item->owner_hash))
-               goto out1;
-
-       list_add_tail(&owner_item->sman_list, &sman->owner_items);
-       return owner_item;
-
-out1:
-       kfree(owner_item);
-out:
-       return NULL;
-}
-
-struct drm_memblock_item *drm_sman_alloc(struct drm_sman *sman, unsigned int manager,
-                                   unsigned long size, unsigned alignment,
-                                   unsigned long owner)
-{
-       void *tmp;
-       struct drm_sman_mm *sman_mm;
-       struct drm_owner_item *owner_item;
-       struct drm_memblock_item *memblock;
-
-       BUG_ON(manager >= sman->num_managers);
-
-       sman_mm = &sman->mm[manager];
-       tmp = sman_mm->allocate(sman_mm->private, size, alignment);
-
-       if (!tmp) {
-               return NULL;
-       }
-
-       memblock = kzalloc(sizeof(*memblock), GFP_KERNEL);
-
-       if (!memblock)
-               goto out;
-
-       memblock->mm_info = tmp;
-       memblock->mm = sman_mm;
-       memblock->sman = sman;
-
-       if (drm_ht_just_insert_please
-           (&sman->user_hash_tab, &memblock->user_hash,
-            (unsigned long)memblock, 32, 0, 0))
-               goto out1;
-
-       owner_item = drm_sman_get_owner_item(sman, owner);
-       if (!owner_item)
-               goto out2;
-
-       list_add_tail(&memblock->owner_list, &owner_item->mem_blocks);
-
-       return memblock;
-
-out2:
-       drm_ht_remove_item(&sman->user_hash_tab, &memblock->user_hash);
-out1:
-       kfree(memblock);
-out:
-       sman_mm->free(sman_mm->private, tmp);
-
-       return NULL;
-}
-
-EXPORT_SYMBOL(drm_sman_alloc);
-
-static void drm_sman_free(struct drm_memblock_item *item)
-{
-       struct drm_sman *sman = item->sman;
-
-       list_del(&item->owner_list);
-       drm_ht_remove_item(&sman->user_hash_tab, &item->user_hash);
-       item->mm->free(item->mm->private, item->mm_info);
-       kfree(item);
-}
-
-int drm_sman_free_key(struct drm_sman *sman, unsigned int key)
-{
-       struct drm_hash_item *hash_item;
-       struct drm_memblock_item *memblock_item;
-
-       if (drm_ht_find_item(&sman->user_hash_tab, key, &hash_item))
-               return -EINVAL;
-
-       memblock_item = drm_hash_entry(hash_item, struct drm_memblock_item,
-                                      user_hash);
-       drm_sman_free(memblock_item);
-       return 0;
-}
-
-EXPORT_SYMBOL(drm_sman_free_key);
-
-static void drm_sman_remove_owner(struct drm_sman *sman,
-                                 struct drm_owner_item *owner_item)
-{
-       list_del(&owner_item->sman_list);
-       drm_ht_remove_item(&sman->owner_hash_tab, &owner_item->owner_hash);
-       kfree(owner_item);
-}
-
-int drm_sman_owner_clean(struct drm_sman *sman, unsigned long owner)
-{
-
-       struct drm_hash_item *hash_item;
-       struct drm_owner_item *owner_item;
-
-       if (drm_ht_find_item(&sman->owner_hash_tab, owner, &hash_item)) {
-               return -1;
-       }
-
-       owner_item = drm_hash_entry(hash_item, struct drm_owner_item, owner_hash);
-       if (owner_item->mem_blocks.next == &owner_item->mem_blocks) {
-               drm_sman_remove_owner(sman, owner_item);
-               return -1;
-       }
-
-       return 0;
-}
-
-EXPORT_SYMBOL(drm_sman_owner_clean);
-
-static void drm_sman_do_owner_cleanup(struct drm_sman *sman,
-                                     struct drm_owner_item *owner_item)
-{
-       struct drm_memblock_item *entry, *next;
-
-       list_for_each_entry_safe(entry, next, &owner_item->mem_blocks,
-                                owner_list) {
-               drm_sman_free(entry);
-       }
-       drm_sman_remove_owner(sman, owner_item);
-}
-
-void drm_sman_owner_cleanup(struct drm_sman *sman, unsigned long owner)
-{
-
-       struct drm_hash_item *hash_item;
-       struct drm_owner_item *owner_item;
-
-       if (drm_ht_find_item(&sman->owner_hash_tab, owner, &hash_item)) {
-
-               return;
-       }
-
-       owner_item = drm_hash_entry(hash_item, struct drm_owner_item, owner_hash);
-       drm_sman_do_owner_cleanup(sman, owner_item);
-}
-
-EXPORT_SYMBOL(drm_sman_owner_cleanup);
-
-void drm_sman_cleanup(struct drm_sman *sman)
-{
-       struct drm_owner_item *entry, *next;
-       unsigned int i;
-       struct drm_sman_mm *sman_mm;
-
-       list_for_each_entry_safe(entry, next, &sman->owner_items, sman_list) {
-               drm_sman_do_owner_cleanup(sman, entry);
-       }
-       if (sman->mm) {
-               for (i = 0; i < sman->num_managers; ++i) {
-                       sman_mm = &sman->mm[i];
-                       if (sman_mm->private) {
-                               sman_mm->destroy(sman_mm->private);
-                               sman_mm->private = NULL;
-                       }
-               }
-       }
-}
-
-EXPORT_SYMBOL(drm_sman_cleanup);
diff --git a/services4/3rdparty/linux_drm/drm_stub.c b/services4/3rdparty/linux_drm/drm_stub.c
deleted file mode 100644 (file)
index cdc89ee..0000000
+++ /dev/null
@@ -1,474 +0,0 @@
-/**
- * \file drm_stub.h
- * Stub support
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- */
-
-/*
- * Created: Fri Jan 19 10:48:35 2001 by faith@acm.org
- *
- * Copyright 2001 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
- * DEALINGS IN THE SOFTWARE.
- */
-
-#include <linux/module.h>
-#include <linux/moduleparam.h>
-#include <linux/slab.h>
-#include "drmP.h"
-#include "drm_core.h"
-
-unsigned int drm_debug = 0;    /* 1 to enable debug output */
-EXPORT_SYMBOL(drm_debug);
-
-MODULE_AUTHOR(CORE_AUTHOR);
-MODULE_DESCRIPTION(CORE_DESC);
-MODULE_LICENSE("GPL and additional rights");
-MODULE_PARM_DESC(debug, "Enable debug output");
-
-module_param_named(debug, drm_debug, int, 0600);
-
-struct idr drm_minors_idr;
-
-struct class *drm_class;
-struct proc_dir_entry *drm_proc_root;
-struct dentry *drm_debugfs_root;
-void drm_ut_debug_printk(unsigned int request_level,
-                        const char *prefix,
-                        const char *function_name,
-                        const char *format, ...)
-{
-       va_list args;
-
-       if (drm_debug & request_level) {
-               if (function_name)
-                       printk(KERN_DEBUG "[%s:%s], ", prefix, function_name);
-               va_start(args, format);
-               vprintk(format, args);
-               va_end(args);
-       }
-}
-EXPORT_SYMBOL(drm_ut_debug_printk);
-static int drm_minor_get_id(struct drm_device *dev, int type)
-{
-       int new_id;
-       int ret;
-       int base = 0, limit = 63;
-
-       if (type == DRM_MINOR_CONTROL) {
-                base += 64;
-                limit = base + 127;
-        } else if (type == DRM_MINOR_RENDER) {
-                base += 128;
-                limit = base + 255;
-        }
-
-again:
-       if (idr_pre_get(&drm_minors_idr, GFP_KERNEL) == 0) {
-               DRM_ERROR("Out of memory expanding drawable idr\n");
-               return -ENOMEM;
-       }
-       mutex_lock(&dev->struct_mutex);
-       ret = idr_get_new_above(&drm_minors_idr, NULL,
-                               base, &new_id);
-       mutex_unlock(&dev->struct_mutex);
-       if (ret == -EAGAIN) {
-               goto again;
-       } else if (ret) {
-               return ret;
-       }
-
-       if (new_id >= limit) {
-               idr_remove(&drm_minors_idr, new_id);
-               return -EINVAL;
-       }
-       return new_id;
-}
-
-struct drm_master *drm_master_create(struct drm_minor *minor)
-{
-       struct drm_master *master;
-
-       master = kzalloc(sizeof(*master), GFP_KERNEL);
-       if (!master)
-               return NULL;
-
-       kref_init(&master->refcount);
-       spin_lock_init(&master->lock.spinlock);
-       init_waitqueue_head(&master->lock.lock_queue);
-       drm_ht_create(&master->magiclist, DRM_MAGIC_HASH_ORDER);
-       INIT_LIST_HEAD(&master->magicfree);
-       master->minor = minor;
-
-       list_add_tail(&master->head, &minor->master_list);
-
-       return master;
-}
-
-struct drm_master *drm_master_get(struct drm_master *master)
-{
-       kref_get(&master->refcount);
-       return master;
-}
-EXPORT_SYMBOL(drm_master_get);
-
-static void drm_master_destroy(struct kref *kref)
-{
-       struct drm_master *master = container_of(kref, struct drm_master, refcount);
-       struct drm_magic_entry *pt, *next;
-       struct drm_device *dev = master->minor->dev;
-       struct drm_map_list *r_list, *list_temp;
-
-       list_del(&master->head);
-
-       if (dev->driver->master_destroy)
-               dev->driver->master_destroy(dev, master);
-
-       list_for_each_entry_safe(r_list, list_temp, &dev->maplist, head) {
-               if (r_list->master == master) {
-                       drm_rmmap_locked(dev, r_list->map);
-                       r_list = NULL;
-               }
-       }
-
-       if (master->unique) {
-               kfree(master->unique);
-               master->unique = NULL;
-               master->unique_len = 0;
-       }
-
-       kfree(dev->devname);
-       dev->devname = NULL;
-
-       list_for_each_entry_safe(pt, next, &master->magicfree, head) {
-               list_del(&pt->head);
-               drm_ht_remove_item(&master->magiclist, &pt->hash_item);
-               kfree(pt);
-       }
-
-       drm_ht_remove(&master->magiclist);
-
-       kfree(master);
-}
-
-void drm_master_put(struct drm_master **master)
-{
-       kref_put(&(*master)->refcount, drm_master_destroy);
-       *master = NULL;
-}
-EXPORT_SYMBOL(drm_master_put);
-
-int drm_setmaster_ioctl(struct drm_device *dev, void *data,
-                       struct drm_file *file_priv)
-{
-       int ret = 0;
-
-       if (file_priv->is_master)
-               return 0;
-
-       if (file_priv->minor->master && file_priv->minor->master != file_priv->master)
-               return -EINVAL;
-
-       if (!file_priv->master)
-               return -EINVAL;
-
-       if (!file_priv->minor->master &&
-           file_priv->minor->master != file_priv->master) {
-               mutex_lock(&dev->struct_mutex);
-               file_priv->minor->master = drm_master_get(file_priv->master);
-               file_priv->is_master = 1;
-               if (dev->driver->master_set) {
-                       ret = dev->driver->master_set(dev, file_priv, false);
-                       if (unlikely(ret != 0)) {
-                               file_priv->is_master = 0;
-                               drm_master_put(&file_priv->minor->master);
-                       }
-               }
-               mutex_unlock(&dev->struct_mutex);
-       }
-
-       return 0;
-}
-
-int drm_dropmaster_ioctl(struct drm_device *dev, void *data,
-                        struct drm_file *file_priv)
-{
-       if (!file_priv->is_master)
-               return -EINVAL;
-
-       if (!file_priv->minor->master)
-               return -EINVAL;
-
-       mutex_lock(&dev->struct_mutex);
-       if (dev->driver->master_drop)
-               dev->driver->master_drop(dev, file_priv, false);
-       drm_master_put(&file_priv->minor->master);
-       file_priv->is_master = 0;
-       mutex_unlock(&dev->struct_mutex);
-       return 0;
-}
-
-int drm_fill_in_dev(struct drm_device *dev,
-                          const struct pci_device_id *ent,
-                          struct drm_driver *driver)
-{
-       int retcode;
-
-       INIT_LIST_HEAD(&dev->filelist);
-       INIT_LIST_HEAD(&dev->ctxlist);
-       INIT_LIST_HEAD(&dev->vmalist);
-       INIT_LIST_HEAD(&dev->maplist);
-       INIT_LIST_HEAD(&dev->vblank_event_list);
-
-       spin_lock_init(&dev->count_lock);
-       spin_lock_init(&dev->event_lock);
-       mutex_init(&dev->struct_mutex);
-       mutex_init(&dev->ctxlist_mutex);
-
-       if (drm_ht_create(&dev->map_hash, 12)) {
-               return -ENOMEM;
-       }
-
-       /* the DRM has 6 basic counters */
-       dev->counters = 6;
-       dev->types[0] = _DRM_STAT_LOCK;
-       dev->types[1] = _DRM_STAT_OPENS;
-       dev->types[2] = _DRM_STAT_CLOSES;
-       dev->types[3] = _DRM_STAT_IOCTLS;
-       dev->types[4] = _DRM_STAT_LOCKS;
-       dev->types[5] = _DRM_STAT_UNLOCKS;
-
-       dev->driver = driver;
-
-       if (drm_core_has_AGP(dev)) {
-               if (drm_device_is_agp(dev))
-                       dev->agp = drm_agp_init(dev);
-               if (drm_core_check_feature(dev, DRIVER_REQUIRE_AGP)
-                   && (dev->agp == NULL)) {
-                       DRM_ERROR("Cannot initialize the agpgart module.\n");
-                       retcode = -EINVAL;
-                       goto error_out_unreg;
-               }
-               if (drm_core_has_MTRR(dev)) {
-                       if (dev->agp)
-                               dev->agp->agp_mtrr =
-                                   mtrr_add(dev->agp->agp_info.aper_base,
-                                            dev->agp->agp_info.aper_size *
-                                            1024 * 1024, MTRR_TYPE_WRCOMB, 1);
-               }
-       }
-
-
-       retcode = drm_ctxbitmap_init(dev);
-       if (retcode) {
-               DRM_ERROR("Cannot allocate memory for context bitmap.\n");
-               goto error_out_unreg;
-       }
-
-       if (driver->driver_features & DRIVER_GEM) {
-               retcode = drm_gem_init(dev);
-               if (retcode) {
-                       DRM_ERROR("Cannot initialize graphics execution "
-                                 "manager (GEM)\n");
-                       goto error_out_unreg;
-               }
-       }
-
-       return 0;
-
-      error_out_unreg:
-       drm_lastclose(dev);
-       return retcode;
-}
-
-
-/**
- * Get a secondary minor number.
- *
- * \param dev device data structure
- * \param sec-minor structure to hold the assigned minor
- * \return negative number on failure.
- *
- * Search an empty entry and initialize it to the given parameters, and
- * create the proc init entry via proc_init(). This routines assigns
- * minor numbers to secondary heads of multi-headed cards
- */
-int drm_get_minor(struct drm_device *dev, struct drm_minor **minor, int type)
-{
-       struct drm_minor *new_minor;
-       int ret;
-       int minor_id;
-
-       DRM_DEBUG("\n");
-
-       minor_id = drm_minor_get_id(dev, type);
-       if (minor_id < 0)
-               return minor_id;
-
-       new_minor = kzalloc(sizeof(struct drm_minor), GFP_KERNEL);
-       if (!new_minor) {
-               ret = -ENOMEM;
-               goto err_idr;
-       }
-
-       new_minor->type = type;
-       new_minor->device = MKDEV(DRM_MAJOR, minor_id);
-       new_minor->dev = dev;
-       new_minor->index = minor_id;
-       INIT_LIST_HEAD(&new_minor->master_list);
-
-       idr_replace(&drm_minors_idr, new_minor, minor_id);
-
-       if (type == DRM_MINOR_LEGACY) {
-               ret = drm_proc_init(new_minor, minor_id, drm_proc_root);
-               if (ret) {
-                       DRM_ERROR("DRM: Failed to initialize /proc/dri.\n");
-                       goto err_mem;
-               }
-       } else
-               new_minor->proc_root = NULL;
-
-#if defined(CONFIG_DEBUG_FS)
-       ret = drm_debugfs_init(new_minor, minor_id, drm_debugfs_root);
-       if (ret) {
-               DRM_ERROR("DRM: Failed to initialize /sys/kernel/debug/dri.\n");
-               goto err_g2;
-       }
-#endif
-
-       ret = drm_sysfs_device_add(new_minor);
-       if (ret) {
-               printk(KERN_ERR
-                      "DRM: Error sysfs_device_add.\n");
-               goto err_g2;
-       }
-       *minor = new_minor;
-
-       DRM_DEBUG("new minor assigned %d\n", minor_id);
-       return 0;
-
-
-err_g2:
-       if (new_minor->type == DRM_MINOR_LEGACY)
-               drm_proc_cleanup(new_minor, drm_proc_root);
-err_mem:
-       kfree(new_minor);
-err_idr:
-       idr_remove(&drm_minors_idr, minor_id);
-       *minor = NULL;
-       return ret;
-}
-
-/**
- * Put a secondary minor number.
- *
- * \param sec_minor - structure to be released
- * \return always zero
- *
- * Cleans up the proc resources. Not legal for this to be the
- * last minor released.
- *
- */
-int drm_put_minor(struct drm_minor **minor_p)
-{
-       struct drm_minor *minor = *minor_p;
-
-       DRM_DEBUG("release secondary minor %d\n", minor->index);
-
-       if (minor->type == DRM_MINOR_LEGACY)
-               drm_proc_cleanup(minor, drm_proc_root);
-#if defined(CONFIG_DEBUG_FS)
-       drm_debugfs_cleanup(minor);
-#endif
-
-       drm_sysfs_device_remove(minor);
-
-       idr_remove(&drm_minors_idr, minor->index);
-
-       kfree(minor);
-       *minor_p = NULL;
-       return 0;
-}
-
-/**
- * Called via drm_exit() at module unload time or when pci device is
- * unplugged.
- *
- * Cleans up all DRM device, calling drm_lastclose().
- *
- * \sa drm_init
- */
-void drm_put_dev(struct drm_device *dev)
-{
-       struct drm_driver *driver;
-       struct drm_map_list *r_list, *list_temp;
-
-       DRM_DEBUG("\n");
-
-       if (!dev) {
-               DRM_ERROR("cleanup called no dev\n");
-               return;
-       }
-       driver = dev->driver;
-
-       drm_lastclose(dev);
-
-       if (drm_core_has_MTRR(dev) && drm_core_has_AGP(dev) &&
-           dev->agp && dev->agp->agp_mtrr >= 0) {
-               int retval;
-               retval = mtrr_del(dev->agp->agp_mtrr,
-                                 dev->agp->agp_info.aper_base,
-                                 dev->agp->agp_info.aper_size * 1024 * 1024);
-               DRM_DEBUG("mtrr_del=%d\n", retval);
-       }
-
-       if (dev->driver->unload)
-               dev->driver->unload(dev);
-
-       if (drm_core_has_AGP(dev) && dev->agp) {
-               kfree(dev->agp);
-               dev->agp = NULL;
-       }
-
-       drm_vblank_cleanup(dev);
-
-       list_for_each_entry_safe(r_list, list_temp, &dev->maplist, head)
-               drm_rmmap(dev, r_list->map);
-       drm_ht_remove(&dev->map_hash);
-
-       drm_ctxbitmap_cleanup(dev);
-
-       if (drm_core_check_feature(dev, DRIVER_MODESET))
-               drm_put_minor(&dev->control);
-
-       if (driver->driver_features & DRIVER_GEM)
-               drm_gem_destroy(dev);
-
-       drm_put_minor(&dev->primary);
-
-       if (dev->devname) {
-               kfree(dev->devname);
-               dev->devname = NULL;
-       }
-       kfree(dev);
-}
-EXPORT_SYMBOL(drm_put_dev);
diff --git a/services4/3rdparty/linux_drm/drm_sysfs.c b/services4/3rdparty/linux_drm/drm_sysfs.c
deleted file mode 100644 (file)
index 85da4c4..0000000
+++ /dev/null
@@ -1,553 +0,0 @@
-
-/*
- * drm_sysfs.c - Modifications to drm_sysfs_class.c to support
- *               extra sysfs attribute from DRM. Normal drm_sysfs_class
- *               does not allow adding attributes.
- *
- * Copyright (c) 2004 Jon Smirl <jonsmirl@gmail.com>
- * Copyright (c) 2003-2004 Greg Kroah-Hartman <greg@kroah.com>
- * Copyright (c) 2003-2004 IBM Corp.
- *
- * This file is released under the GPLv2
- *
- */
-
-#include <linux/device.h>
-#include <linux/kdev_t.h>
-#include <linux/gfp.h>
-#include <linux/err.h>
-
-#include "drm_sysfs.h"
-#include "drm_core.h"
-#include "drmP.h"
-
-#define to_drm_minor(d) container_of(d, struct drm_minor, kdev)
-#define to_drm_connector(d) container_of(d, struct drm_connector, kdev)
-
-static struct device_type drm_sysfs_device_minor = {
-       .name = "drm_minor"
-};
-
-/**
- * drm_class_suspend - DRM class suspend hook
- * @dev: Linux device to suspend
- * @state: power state to enter
- *
- * Just figures out what the actual struct drm_device associated with
- * @dev is and calls its suspend hook, if present.
- */
-static int drm_class_suspend(struct device *dev, pm_message_t state)
-{
-       if (dev->type == &drm_sysfs_device_minor) {
-               struct drm_minor *drm_minor = to_drm_minor(dev);
-               struct drm_device *drm_dev = drm_minor->dev;
-
-               if (drm_minor->type == DRM_MINOR_LEGACY &&
-                   !drm_core_check_feature(drm_dev, DRIVER_MODESET) &&
-                   drm_dev->driver->suspend)
-                       return drm_dev->driver->suspend(drm_dev, state);
-       }
-       return 0;
-}
-
-/**
- * drm_class_resume - DRM class resume hook
- * @dev: Linux device to resume
- *
- * Just figures out what the actual struct drm_device associated with
- * @dev is and calls its resume hook, if present.
- */
-static int drm_class_resume(struct device *dev)
-{
-       if (dev->type == &drm_sysfs_device_minor) {
-               struct drm_minor *drm_minor = to_drm_minor(dev);
-               struct drm_device *drm_dev = drm_minor->dev;
-
-               if (drm_minor->type == DRM_MINOR_LEGACY &&
-                   !drm_core_check_feature(drm_dev, DRIVER_MODESET) &&
-                   drm_dev->driver->resume)
-                       return drm_dev->driver->resume(drm_dev);
-       }
-       return 0;
-}
-
-static char *drm_devnode(struct device *dev, mode_t *mode)
-{
-       return kasprintf(GFP_KERNEL, "dri/%s", dev_name(dev));
-}
-
-static CLASS_ATTR_STRING(version, S_IRUGO,
-               CORE_NAME " "
-               __stringify(CORE_MAJOR) "."
-               __stringify(CORE_MINOR) "."
-               __stringify(CORE_PATCHLEVEL) " "
-               CORE_DATE);
-
-/**
- * drm_sysfs_create - create a struct drm_sysfs_class structure
- * @owner: pointer to the module that is to "own" this struct drm_sysfs_class
- * @name: pointer to a string for the name of this class.
- *
- * This is used to create DRM class pointer that can then be used
- * in calls to drm_sysfs_device_add().
- *
- * Note, the pointer created here is to be destroyed when finished by making a
- * call to drm_sysfs_destroy().
- */
-struct class *drm_sysfs_create(struct module *owner, char *name)
-{
-       struct class *class;
-       int err;
-
-       class = class_create(owner, name);
-       if (IS_ERR(class)) {
-               err = PTR_ERR(class);
-               goto err_out;
-       }
-
-       class->suspend = drm_class_suspend;
-       class->resume = drm_class_resume;
-
-       err = class_create_file(class, &class_attr_version.attr);
-       if (err)
-               goto err_out_class;
-
-       class->devnode = drm_devnode;
-
-       return class;
-
-err_out_class:
-       class_destroy(class);
-err_out:
-       return ERR_PTR(err);
-}
-
-/**
- * drm_sysfs_destroy - destroys DRM class
- *
- * Destroy the DRM device class.
- */
-void drm_sysfs_destroy(void)
-{
-       if ((drm_class == NULL) || (IS_ERR(drm_class)))
-               return;
-       class_remove_file(drm_class, &class_attr_version.attr);
-       class_destroy(drm_class);
-}
-
-/**
- * drm_sysfs_device_release - do nothing
- * @dev: Linux device
- *
- * Normally, this would free the DRM device associated with @dev, along
- * with cleaning up any other stuff.  But we do that in the DRM core, so
- * this function can just return and hope that the core does its job.
- */
-static void drm_sysfs_device_release(struct device *dev)
-{
-       memset(dev, 0, sizeof(struct device));
-       return;
-}
-
-/*
- * Connector properties
- */
-static ssize_t status_show(struct device *device,
-                          struct device_attribute *attr,
-                          char *buf)
-{
-       struct drm_connector *connector = to_drm_connector(device);
-       enum drm_connector_status status;
-
-       status = connector->funcs->detect(connector, true);
-       return snprintf(buf, PAGE_SIZE, "%s\n",
-                       drm_get_connector_status_name(status));
-}
-
-static ssize_t dpms_show(struct device *device,
-                          struct device_attribute *attr,
-                          char *buf)
-{
-       struct drm_connector *connector = to_drm_connector(device);
-       struct drm_device *dev = connector->dev;
-       uint64_t dpms_status;
-       int ret;
-
-       ret = drm_connector_property_get_value(connector,
-                                           dev->mode_config.dpms_property,
-                                           &dpms_status);
-       if (ret)
-               return 0;
-
-       return snprintf(buf, PAGE_SIZE, "%s\n",
-                       drm_get_dpms_name((int)dpms_status));
-}
-
-static ssize_t enabled_show(struct device *device,
-                           struct device_attribute *attr,
-                          char *buf)
-{
-       struct drm_connector *connector = to_drm_connector(device);
-
-       return snprintf(buf, PAGE_SIZE, "%s\n", connector->encoder ? "enabled" :
-                       "disabled");
-}
-
-static ssize_t edid_show(struct file *filp, struct kobject *kobj,
-                        struct bin_attribute *attr, char *buf, loff_t off,
-                        size_t count)
-{
-       struct device *connector_dev = container_of(kobj, struct device, kobj);
-       struct drm_connector *connector = to_drm_connector(connector_dev);
-       unsigned char *edid;
-       size_t size;
-
-       if (!connector->edid_blob_ptr)
-               return 0;
-
-       edid = connector->edid_blob_ptr->data;
-       size = connector->edid_blob_ptr->length;
-       if (!edid)
-               return 0;
-
-       if (off >= size)
-               return 0;
-
-       if (off + count > size)
-               count = size - off;
-       memcpy(buf, edid + off, count);
-
-       return count;
-}
-
-static ssize_t modes_show(struct device *device,
-                          struct device_attribute *attr,
-                          char *buf)
-{
-       struct drm_connector *connector = to_drm_connector(device);
-       struct drm_display_mode *mode;
-       int written = 0;
-
-       list_for_each_entry(mode, &connector->modes, head) {
-               written += snprintf(buf + written, PAGE_SIZE - written, "%s\n",
-                                   mode->name);
-       }
-
-       return written;
-}
-
-static ssize_t subconnector_show(struct device *device,
-                          struct device_attribute *attr,
-                          char *buf)
-{
-       struct drm_connector *connector = to_drm_connector(device);
-       struct drm_device *dev = connector->dev;
-       struct drm_property *prop = NULL;
-       uint64_t subconnector;
-       int is_tv = 0;
-       int ret;
-
-       switch (connector->connector_type) {
-               case DRM_MODE_CONNECTOR_DVII:
-                       prop = dev->mode_config.dvi_i_subconnector_property;
-                       break;
-               case DRM_MODE_CONNECTOR_Composite:
-               case DRM_MODE_CONNECTOR_SVIDEO:
-               case DRM_MODE_CONNECTOR_Component:
-               case DRM_MODE_CONNECTOR_TV:
-                       prop = dev->mode_config.tv_subconnector_property;
-                       is_tv = 1;
-                       break;
-               default:
-                       DRM_ERROR("Wrong connector type for this property\n");
-                       return 0;
-       }
-
-       if (!prop) {
-               DRM_ERROR("Unable to find subconnector property\n");
-               return 0;
-       }
-
-       ret = drm_connector_property_get_value(connector, prop, &subconnector);
-       if (ret)
-               return 0;
-
-       return snprintf(buf, PAGE_SIZE, "%s", is_tv ?
-                       drm_get_tv_subconnector_name((int)subconnector) :
-                       drm_get_dvi_i_subconnector_name((int)subconnector));
-}
-
-static ssize_t select_subconnector_show(struct device *device,
-                          struct device_attribute *attr,
-                          char *buf)
-{
-       struct drm_connector *connector = to_drm_connector(device);
-       struct drm_device *dev = connector->dev;
-       struct drm_property *prop = NULL;
-       uint64_t subconnector;
-       int is_tv = 0;
-       int ret;
-
-       switch (connector->connector_type) {
-               case DRM_MODE_CONNECTOR_DVII:
-                       prop = dev->mode_config.dvi_i_select_subconnector_property;
-                       break;
-               case DRM_MODE_CONNECTOR_Composite:
-               case DRM_MODE_CONNECTOR_SVIDEO:
-               case DRM_MODE_CONNECTOR_Component:
-               case DRM_MODE_CONNECTOR_TV:
-                       prop = dev->mode_config.tv_select_subconnector_property;
-                       is_tv = 1;
-                       break;
-               default:
-                       DRM_ERROR("Wrong connector type for this property\n");
-                       return 0;
-       }
-
-       if (!prop) {
-               DRM_ERROR("Unable to find select subconnector property\n");
-               return 0;
-       }
-
-       ret = drm_connector_property_get_value(connector, prop, &subconnector);
-       if (ret)
-               return 0;
-
-       return snprintf(buf, PAGE_SIZE, "%s", is_tv ?
-                       drm_get_tv_select_name((int)subconnector) :
-                       drm_get_dvi_i_select_name((int)subconnector));
-}
-
-static struct device_attribute connector_attrs[] = {
-       __ATTR_RO(status),
-       __ATTR_RO(enabled),
-       __ATTR_RO(dpms),
-       __ATTR_RO(modes),
-};
-
-/* These attributes are for both DVI-I connectors and all types of tv-out. */
-static struct device_attribute connector_attrs_opt1[] = {
-       __ATTR_RO(subconnector),
-       __ATTR_RO(select_subconnector),
-};
-
-static struct bin_attribute edid_attr = {
-       .attr.name = "edid",
-       .attr.mode = 0444,
-       .size = 0,
-       .read = edid_show,
-};
-
-/**
- * drm_sysfs_connector_add - add an connector to sysfs
- * @connector: connector to add
- *
- * Create an connector device in sysfs, along with its associated connector
- * properties (so far, connection status, dpms, mode list & edid) and
- * generate a hotplug event so userspace knows there's a new connector
- * available.
- *
- * Note:
- * This routine should only be called *once* for each DRM minor registered.
- * A second call for an already registered device will trigger the BUG_ON
- * below.
- */
-int drm_sysfs_connector_add(struct drm_connector *connector)
-{
-       struct drm_device *dev = connector->dev;
-       int attr_cnt = 0;
-       int opt_cnt = 0;
-       int i;
-       int ret = 0;
-
-       /* We shouldn't get called more than once for the same connector */
-       BUG_ON(device_is_registered(&connector->kdev));
-
-       connector->kdev.parent = &dev->primary->kdev;
-       connector->kdev.class = drm_class;
-       connector->kdev.release = drm_sysfs_device_release;
-
-       DRM_DEBUG("adding \"%s\" to sysfs\n",
-                 drm_get_connector_name(connector));
-
-       dev_set_name(&connector->kdev, "card%d-%s",
-                    dev->primary->index, drm_get_connector_name(connector));
-       ret = device_register(&connector->kdev);
-
-       if (ret) {
-               DRM_ERROR("failed to register connector device: %d\n", ret);
-               goto out;
-       }
-
-       /* Standard attributes */
-
-       for (attr_cnt = 0; attr_cnt < ARRAY_SIZE(connector_attrs); attr_cnt++) {
-               ret = device_create_file(&connector->kdev, &connector_attrs[attr_cnt]);
-               if (ret)
-                       goto err_out_files;
-       }
-
-       /* Optional attributes */
-       /*
-        * In the long run it maybe a good idea to make one set of
-        * optionals per connector type.
-        */
-       switch (connector->connector_type) {
-               case DRM_MODE_CONNECTOR_DVII:
-               case DRM_MODE_CONNECTOR_Composite:
-               case DRM_MODE_CONNECTOR_SVIDEO:
-               case DRM_MODE_CONNECTOR_Component:
-               case DRM_MODE_CONNECTOR_TV:
-                       for (opt_cnt = 0; opt_cnt < ARRAY_SIZE(connector_attrs_opt1); opt_cnt++) {
-                               ret = device_create_file(&connector->kdev, &connector_attrs_opt1[opt_cnt]);
-                               if (ret)
-                                       goto err_out_files;
-                       }
-                       break;
-               default:
-                       break;
-       }
-
-       ret = sysfs_create_bin_file(&connector->kdev.kobj, &edid_attr);
-       if (ret)
-               goto err_out_files;
-
-       /* Let userspace know we have a new connector */
-       drm_sysfs_hotplug_event(dev);
-
-       return 0;
-
-err_out_files:
-       for (i = 0; i < opt_cnt; i++)
-               device_remove_file(&connector->kdev, &connector_attrs_opt1[i]);
-       for (i = 0; i < attr_cnt; i++)
-               device_remove_file(&connector->kdev, &connector_attrs[i]);
-       device_unregister(&connector->kdev);
-
-out:
-       return ret;
-}
-EXPORT_SYMBOL(drm_sysfs_connector_add);
-
-/**
- * drm_sysfs_connector_remove - remove an connector device from sysfs
- * @connector: connector to remove
- *
- * Remove @connector and its associated attributes from sysfs.  Note that
- * the device model core will take care of sending the "remove" uevent
- * at this time, so we don't need to do it.
- *
- * Note:
- * This routine should only be called if the connector was previously
- * successfully registered.  If @connector hasn't been registered yet,
- * you'll likely see a panic somewhere deep in sysfs code when called.
- */
-void drm_sysfs_connector_remove(struct drm_connector *connector)
-{
-       int i;
-
-       DRM_DEBUG("removing \"%s\" from sysfs\n",
-                 drm_get_connector_name(connector));
-
-       for (i = 0; i < ARRAY_SIZE(connector_attrs); i++)
-               device_remove_file(&connector->kdev, &connector_attrs[i]);
-       sysfs_remove_bin_file(&connector->kdev.kobj, &edid_attr);
-       device_unregister(&connector->kdev);
-}
-EXPORT_SYMBOL(drm_sysfs_connector_remove);
-
-/**
- * drm_sysfs_hotplug_event - generate a DRM uevent
- * @dev: DRM device
- *
- * Send a uevent for the DRM device specified by @dev.  Currently we only
- * set HOTPLUG=1 in the uevent environment, but this could be expanded to
- * deal with other types of events.
- */
-void drm_sysfs_hotplug_event(struct drm_device *dev)
-{
-       char *event_string = "HOTPLUG=1";
-       char *envp[] = { event_string, NULL };
-
-       DRM_DEBUG("generating hotplug event\n");
-
-       kobject_uevent_env(&dev->primary->kdev.kobj, KOBJ_CHANGE, envp);
-}
-EXPORT_SYMBOL(drm_sysfs_hotplug_event);
-
-/**
- * drm_sysfs_device_add - adds a class device to sysfs for a character driver
- * @dev: DRM device to be added
- * @head: DRM head in question
- *
- * Add a DRM device to the DRM's device model class.  We use @dev's PCI device
- * as the parent for the Linux device, and make sure it has a file containing
- * the driver we're using (for userspace compatibility).
- */
-int drm_sysfs_device_add(struct drm_minor *minor)
-{
-       int err;
-       char *minor_str;
-
-       minor->kdev.parent = minor->dev->dev;
-
-       minor->kdev.class = drm_class;
-       minor->kdev.release = drm_sysfs_device_release;
-       minor->kdev.devt = minor->device;
-       minor->kdev.type = &drm_sysfs_device_minor;
-       if (minor->type == DRM_MINOR_CONTROL)
-               minor_str = "controlD%d";
-        else if (minor->type == DRM_MINOR_RENDER)
-                minor_str = "renderD%d";
-        else
-                minor_str = "card%d";
-
-       dev_set_name(&minor->kdev, minor_str, minor->index);
-
-       err = device_register(&minor->kdev);
-       if (err) {
-               DRM_ERROR("device add failed: %d\n", err);
-               goto err_out;
-       }
-
-       return 0;
-
-err_out:
-       return err;
-}
-
-/**
- * drm_sysfs_device_remove - remove DRM device
- * @dev: DRM device to remove
- *
- * This call unregisters and cleans up a class device that was created with a
- * call to drm_sysfs_device_add()
- */
-void drm_sysfs_device_remove(struct drm_minor *minor)
-{
-       device_unregister(&minor->kdev);
-}
-
-
-/**
- * drm_class_device_register - Register a struct device in the drm class.
- *
- * @dev: pointer to struct device to register.
- *
- * @dev should have all relevant members pre-filled with the exception
- * of the class member. In particular, the device_type member must
- * be set.
- */
-
-int drm_class_device_register(struct device *dev)
-{
-       dev->class = drm_class;
-       return device_register(dev);
-}
-EXPORT_SYMBOL_GPL(drm_class_device_register);
-
-void drm_class_device_unregister(struct device *dev)
-{
-       return device_unregister(dev);
-}
-EXPORT_SYMBOL_GPL(drm_class_device_unregister);
diff --git a/services4/3rdparty/linux_drm/drm_trace_points.c b/services4/3rdparty/linux_drm/drm_trace_points.c
deleted file mode 100644 (file)
index 0d0eb90..0000000
+++ /dev/null
@@ -1,4 +0,0 @@
-#include "drmP.h"
-
-#define CREATE_TRACE_POINTS
-#include "drm_trace.h"
diff --git a/services4/3rdparty/linux_drm/drm_vm.c b/services4/3rdparty/linux_drm/drm_vm.c
deleted file mode 100644 (file)
index 2c3fcbd..0000000
+++ /dev/null
@@ -1,690 +0,0 @@
-/**
- * \file drm_vm.c
- * Memory mapping for DRM
- *
- * \author Rickard E. (Rik) Faith <faith@valinux.com>
- * \author Gareth Hughes <gareth@valinux.com>
- */
-
-/*
- * Created: Mon Jan  4 08:58:31 1999 by faith@valinux.com
- *
- * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
- * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
- * All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice (including the next
- * paragraph) shall be included in all copies or substantial portions of the
- * Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
- * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
- * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
- * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include "drmP.h"
-#if defined(__ia64__)
-#include <linux/efi.h>
-#include <linux/slab.h>
-#endif
-
-static void drm_vm_open(struct vm_area_struct *vma);
-static void drm_vm_close(struct vm_area_struct *vma);
-
-static pgprot_t drm_io_prot(uint32_t map_type, struct vm_area_struct *vma)
-{
-       pgprot_t tmp = vm_get_page_prot(vma->vm_flags);
-
-#if defined(__i386__) || defined(__x86_64__)
-       if (boot_cpu_data.x86 > 3 && map_type != _DRM_AGP) {
-               pgprot_val(tmp) |= _PAGE_PCD;
-               pgprot_val(tmp) &= ~_PAGE_PWT;
-       }
-#elif defined(__powerpc__)
-       pgprot_val(tmp) |= _PAGE_NO_CACHE;
-       if (map_type == _DRM_REGISTERS)
-               pgprot_val(tmp) |= _PAGE_GUARDED;
-#elif defined(__ia64__)
-       if (efi_range_is_wc(vma->vm_start, vma->vm_end -
-                                   vma->vm_start))
-               tmp = pgprot_writecombine(tmp);
-       else
-               tmp = pgprot_noncached(tmp);
-#elif defined(__sparc__) || defined(__arm__)
-       tmp = pgprot_noncached(tmp);
-#endif
-       return tmp;
-}
-
-static pgprot_t drm_dma_prot(uint32_t map_type, struct vm_area_struct *vma)
-{
-       pgprot_t tmp = vm_get_page_prot(vma->vm_flags);
-
-#if defined(__powerpc__) && defined(CONFIG_NOT_COHERENT_CACHE)
-       tmp |= _PAGE_NO_CACHE;
-#endif
-       return tmp;
-}
-
-/**
- * \c fault method for AGP virtual memory.
- *
- * \param vma virtual memory area.
- * \param address access address.
- * \return pointer to the page structure.
- *
- * Find the right map and if it's AGP memory find the real physical page to
- * map, get the page, increment the use count and return it.
- */
-#if __OS_HAS_AGP
-static int drm_do_vm_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       struct drm_file *priv = vma->vm_file->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_local_map *map = NULL;
-       struct drm_map_list *r_list;
-       struct drm_hash_item *hash;
-
-       /*
-        * Find the right map
-        */
-       if (!drm_core_has_AGP(dev))
-               goto vm_fault_error;
-
-       if (!dev->agp || !dev->agp->cant_use_aperture)
-               goto vm_fault_error;
-
-       if (drm_ht_find_item(&dev->map_hash, vma->vm_pgoff, &hash))
-               goto vm_fault_error;
-
-       r_list = drm_hash_entry(hash, struct drm_map_list, hash);
-       map = r_list->map;
-
-       if (map && map->type == _DRM_AGP) {
-               /*
-                * Using vm_pgoff as a selector forces us to use this unusual
-                * addressing scheme.
-                */
-               resource_size_t offset = (unsigned long)vmf->virtual_address -
-                       vma->vm_start;
-               resource_size_t baddr = map->offset + offset;
-               struct drm_agp_mem *agpmem;
-               struct page *page;
-
-#ifdef __alpha__
-               /*
-                * Adjust to a bus-relative address
-                */
-               baddr -= dev->hose->mem_space->start;
-#endif
-
-               /*
-                * It's AGP memory - find the real physical page to map
-                */
-               list_for_each_entry(agpmem, &dev->agp->memory, head) {
-                       if (agpmem->bound <= baddr &&
-                           agpmem->bound + agpmem->pages * PAGE_SIZE > baddr)
-                               break;
-               }
-
-               if (&agpmem->head == &dev->agp->memory)
-                       goto vm_fault_error;
-
-               /*
-                * Get the page, inc the use count, and return it
-                */
-               offset = (baddr - agpmem->bound) >> PAGE_SHIFT;
-               page = agpmem->memory->pages[offset];
-               get_page(page);
-               vmf->page = page;
-
-               DRM_DEBUG
-                   ("baddr = 0x%llx page = 0x%p, offset = 0x%llx, count=%d\n",
-                    (unsigned long long)baddr,
-                    agpmem->memory->pages[offset],
-                    (unsigned long long)offset,
-                    page_count(page));
-               return 0;
-       }
-vm_fault_error:
-       return VM_FAULT_SIGBUS; /* Disallow mremap */
-}
-#else                          /* __OS_HAS_AGP */
-static int drm_do_vm_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       return VM_FAULT_SIGBUS;
-}
-#endif                         /* __OS_HAS_AGP */
-
-/**
- * \c nopage method for shared virtual memory.
- *
- * \param vma virtual memory area.
- * \param address access address.
- * \return pointer to the page structure.
- *
- * Get the mapping, find the real physical page to map, get the page, and
- * return it.
- */
-static int drm_do_vm_shm_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       struct drm_local_map *map = vma->vm_private_data;
-       unsigned long offset;
-       unsigned long i;
-       struct page *page;
-
-       if (!map)
-               return VM_FAULT_SIGBUS; /* Nothing allocated */
-
-       offset = (unsigned long)vmf->virtual_address - vma->vm_start;
-       i = (unsigned long)map->handle + offset;
-       page = vmalloc_to_page((void *)i);
-       if (!page)
-               return VM_FAULT_SIGBUS;
-       get_page(page);
-       vmf->page = page;
-
-       DRM_DEBUG("shm_fault 0x%lx\n", offset);
-       return 0;
-}
-
-/**
- * \c close method for shared virtual memory.
- *
- * \param vma virtual memory area.
- *
- * Deletes map information if we are the last
- * person to close a mapping and it's not in the global maplist.
- */
-static void drm_vm_shm_close(struct vm_area_struct *vma)
-{
-       struct drm_file *priv = vma->vm_file->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_vma_entry *pt, *temp;
-       struct drm_local_map *map;
-       struct drm_map_list *r_list;
-       int found_maps = 0;
-
-       DRM_DEBUG("0x%08lx,0x%08lx\n",
-                 vma->vm_start, vma->vm_end - vma->vm_start);
-       atomic_dec(&dev->vma_count);
-
-       map = vma->vm_private_data;
-
-       mutex_lock(&dev->struct_mutex);
-       list_for_each_entry_safe(pt, temp, &dev->vmalist, head) {
-               if (pt->vma->vm_private_data == map)
-                       found_maps++;
-               if (pt->vma == vma) {
-                       list_del(&pt->head);
-                       kfree(pt);
-               }
-       }
-
-       /* We were the only map that was found */
-       if (found_maps == 1 && map->flags & _DRM_REMOVABLE) {
-               /* Check to see if we are in the maplist, if we are not, then
-                * we delete this mappings information.
-                */
-               found_maps = 0;
-               list_for_each_entry(r_list, &dev->maplist, head) {
-                       if (r_list->map == map)
-                               found_maps++;
-               }
-
-               if (!found_maps) {
-                       drm_dma_handle_t dmah;
-
-                       switch (map->type) {
-                       case _DRM_REGISTERS:
-                       case _DRM_FRAME_BUFFER:
-                               if (drm_core_has_MTRR(dev) && map->mtrr >= 0) {
-                                       int retcode;
-                                       retcode = mtrr_del(map->mtrr,
-                                                          map->offset,
-                                                          map->size);
-                                       DRM_DEBUG("mtrr_del = %d\n", retcode);
-                               }
-                               iounmap(map->handle);
-                               break;
-                       case _DRM_SHM:
-                               vfree(map->handle);
-                               break;
-                       case _DRM_AGP:
-                       case _DRM_SCATTER_GATHER:
-                               break;
-                       case _DRM_CONSISTENT:
-                               dmah.vaddr = map->handle;
-                               dmah.busaddr = map->offset;
-                               dmah.size = map->size;
-                               __drm_pci_free(dev, &dmah);
-                               break;
-                       case _DRM_GEM:
-                               DRM_ERROR("tried to rmmap GEM object\n");
-                               break;
-                       }
-                       kfree(map);
-               }
-       }
-       mutex_unlock(&dev->struct_mutex);
-}
-
-/**
- * \c fault method for DMA virtual memory.
- *
- * \param vma virtual memory area.
- * \param address access address.
- * \return pointer to the page structure.
- *
- * Determine the page number from the page offset and get it from drm_device_dma::pagelist.
- */
-static int drm_do_vm_dma_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       struct drm_file *priv = vma->vm_file->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_device_dma *dma = dev->dma;
-       unsigned long offset;
-       unsigned long page_nr;
-       struct page *page;
-
-       if (!dma)
-               return VM_FAULT_SIGBUS; /* Error */
-       if (!dma->pagelist)
-               return VM_FAULT_SIGBUS; /* Nothing allocated */
-
-       offset = (unsigned long)vmf->virtual_address - vma->vm_start;   /* vm_[pg]off[set] should be 0 */
-       page_nr = offset >> PAGE_SHIFT; /* page_nr could just be vmf->pgoff */
-       page = virt_to_page((dma->pagelist[page_nr] + (offset & (~PAGE_MASK))));
-
-       get_page(page);
-       vmf->page = page;
-
-       DRM_DEBUG("dma_fault 0x%lx (page %lu)\n", offset, page_nr);
-       return 0;
-}
-
-/**
- * \c fault method for scatter-gather virtual memory.
- *
- * \param vma virtual memory area.
- * \param address access address.
- * \return pointer to the page structure.
- *
- * Determine the map offset from the page offset and get it from drm_sg_mem::pagelist.
- */
-static int drm_do_vm_sg_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       struct drm_local_map *map = vma->vm_private_data;
-       struct drm_file *priv = vma->vm_file->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_sg_mem *entry = dev->sg;
-       unsigned long offset;
-       unsigned long map_offset;
-       unsigned long page_offset;
-       struct page *page;
-
-       if (!entry)
-               return VM_FAULT_SIGBUS; /* Error */
-       if (!entry->pagelist)
-               return VM_FAULT_SIGBUS; /* Nothing allocated */
-
-       offset = (unsigned long)vmf->virtual_address - vma->vm_start;
-       map_offset = map->offset - (unsigned long)dev->sg->virtual;
-       page_offset = (offset >> PAGE_SHIFT) + (map_offset >> PAGE_SHIFT);
-       page = entry->pagelist[page_offset];
-       get_page(page);
-       vmf->page = page;
-
-       return 0;
-}
-
-static int drm_vm_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       return drm_do_vm_fault(vma, vmf);
-}
-
-static int drm_vm_shm_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       return drm_do_vm_shm_fault(vma, vmf);
-}
-
-static int drm_vm_dma_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       return drm_do_vm_dma_fault(vma, vmf);
-}
-
-static int drm_vm_sg_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
-{
-       return drm_do_vm_sg_fault(vma, vmf);
-}
-
-/** AGP virtual memory operations */
-static const struct vm_operations_struct drm_vm_ops = {
-       .fault = drm_vm_fault,
-       .open = drm_vm_open,
-       .close = drm_vm_close,
-};
-
-/** Shared virtual memory operations */
-static const struct vm_operations_struct drm_vm_shm_ops = {
-       .fault = drm_vm_shm_fault,
-       .open = drm_vm_open,
-       .close = drm_vm_shm_close,
-};
-
-/** DMA virtual memory operations */
-static const struct vm_operations_struct drm_vm_dma_ops = {
-       .fault = drm_vm_dma_fault,
-       .open = drm_vm_open,
-       .close = drm_vm_close,
-};
-
-/** Scatter-gather virtual memory operations */
-static const struct vm_operations_struct drm_vm_sg_ops = {
-       .fault = drm_vm_sg_fault,
-       .open = drm_vm_open,
-       .close = drm_vm_close,
-};
-
-/**
- * \c open method for shared virtual memory.
- *
- * \param vma virtual memory area.
- *
- * Create a new drm_vma_entry structure as the \p vma private data entry and
- * add it to drm_device::vmalist.
- */
-void drm_vm_open_locked(struct vm_area_struct *vma)
-{
-       struct drm_file *priv = vma->vm_file->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_vma_entry *vma_entry;
-
-       DRM_DEBUG("0x%08lx,0x%08lx\n",
-                 vma->vm_start, vma->vm_end - vma->vm_start);
-       atomic_inc(&dev->vma_count);
-
-       vma_entry = kmalloc(sizeof(*vma_entry), GFP_KERNEL);
-       if (vma_entry) {
-               vma_entry->vma = vma;
-               vma_entry->pid = current->pid;
-               list_add(&vma_entry->head, &dev->vmalist);
-       }
-}
-
-static void drm_vm_open(struct vm_area_struct *vma)
-{
-       struct drm_file *priv = vma->vm_file->private_data;
-       struct drm_device *dev = priv->minor->dev;
-
-       mutex_lock(&dev->struct_mutex);
-       drm_vm_open_locked(vma);
-       mutex_unlock(&dev->struct_mutex);
-}
-
-void drm_vm_close_locked(struct vm_area_struct *vma)
-{
-       struct drm_file *priv = vma->vm_file->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_vma_entry *pt, *temp;
-
-       DRM_DEBUG("0x%08lx,0x%08lx\n",
-                 vma->vm_start, vma->vm_end - vma->vm_start);
-       atomic_dec(&dev->vma_count);
-
-       list_for_each_entry_safe(pt, temp, &dev->vmalist, head) {
-               if (pt->vma == vma) {
-                       list_del(&pt->head);
-                       kfree(pt);
-                       break;
-               }
-       }
-}
-
-/**
- * \c close method for all virtual memory types.
- *
- * \param vma virtual memory area.
- *
- * Search the \p vma private data entry in drm_device::vmalist, unlink it, and
- * free it.
- */
-static void drm_vm_close(struct vm_area_struct *vma)
-{
-       struct drm_file *priv = vma->vm_file->private_data;
-       struct drm_device *dev = priv->minor->dev;
-
-       mutex_lock(&dev->struct_mutex);
-       drm_vm_close_locked(vma);
-       mutex_unlock(&dev->struct_mutex);
-}
-
-/**
- * mmap DMA memory.
- *
- * \param file_priv DRM file private.
- * \param vma virtual memory area.
- * \return zero on success or a negative number on failure.
- *
- * Sets the virtual memory area operations structure to vm_dma_ops, the file
- * pointer, and calls vm_open().
- */
-static int drm_mmap_dma(struct file *filp, struct vm_area_struct *vma)
-{
-       struct drm_file *priv = filp->private_data;
-       struct drm_device *dev;
-       struct drm_device_dma *dma;
-       unsigned long length = vma->vm_end - vma->vm_start;
-
-       dev = priv->minor->dev;
-       dma = dev->dma;
-       DRM_DEBUG("start = 0x%lx, end = 0x%lx, page offset = 0x%lx\n",
-                 vma->vm_start, vma->vm_end, vma->vm_pgoff);
-
-       /* Length must match exact page count */
-       if (!dma || (length >> PAGE_SHIFT) != dma->page_count) {
-               return -EINVAL;
-       }
-
-       if (!capable(CAP_SYS_ADMIN) &&
-           (dma->flags & _DRM_DMA_USE_PCI_RO)) {
-               vma->vm_flags &= ~(VM_WRITE | VM_MAYWRITE);
-#if defined(__i386__) || defined(__x86_64__)
-               pgprot_val(vma->vm_page_prot) &= ~_PAGE_RW;
-#else
-               /* Ye gads this is ugly.  With more thought
-                  we could move this up higher and use
-                  `protection_map' instead.  */
-               vma->vm_page_prot =
-                   __pgprot(pte_val
-                            (pte_wrprotect
-                             (__pte(pgprot_val(vma->vm_page_prot)))));
-#endif
-       }
-
-       vma->vm_ops = &drm_vm_dma_ops;
-
-       vma->vm_flags |= VM_RESERVED;   /* Don't swap */
-       vma->vm_flags |= VM_DONTEXPAND;
-
-       vma->vm_file = filp;    /* Needed for drm_vm_open() */
-       drm_vm_open_locked(vma);
-       return 0;
-}
-
-static resource_size_t drm_core_get_reg_ofs(struct drm_device *dev)
-{
-#ifdef __alpha__
-       return dev->hose->dense_mem_base - dev->hose->mem_space->start;
-#else
-       return 0;
-#endif
-}
-
-/**
- * mmap DMA memory.
- *
- * \param file_priv DRM file private.
- * \param vma virtual memory area.
- * \return zero on success or a negative number on failure.
- *
- * If the virtual memory area has no offset associated with it then it's a DMA
- * area, so calls mmap_dma(). Otherwise searches the map in drm_device::maplist,
- * checks that the restricted flag is not set, sets the virtual memory operations
- * according to the mapping type and remaps the pages. Finally sets the file
- * pointer and calls vm_open().
- */
-int drm_mmap_locked(struct file *filp, struct vm_area_struct *vma)
-{
-       struct drm_file *priv = filp->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       struct drm_local_map *map = NULL;
-       resource_size_t offset = 0;
-       struct drm_hash_item *hash;
-
-       DRM_DEBUG("start = 0x%lx, end = 0x%lx, page offset = 0x%lx\n",
-                 vma->vm_start, vma->vm_end, vma->vm_pgoff);
-
-       if (!priv->authenticated)
-               return -EACCES;
-
-       /* We check for "dma". On Apple's UniNorth, it's valid to have
-        * the AGP mapped at physical address 0
-        * --BenH.
-        */
-       if (!vma->vm_pgoff
-#if __OS_HAS_AGP
-           && (!dev->agp
-               || dev->agp->agp_info.device->vendor != PCI_VENDOR_ID_APPLE)
-#endif
-           )
-               return drm_mmap_dma(filp, vma);
-
-       if (drm_ht_find_item(&dev->map_hash, vma->vm_pgoff, &hash)) {
-               DRM_ERROR("Could not find map\n");
-               return -EINVAL;
-       }
-
-       map = drm_hash_entry(hash, struct drm_map_list, hash)->map;
-       if (!map || ((map->flags & _DRM_RESTRICTED) && !capable(CAP_SYS_ADMIN)))
-               return -EPERM;
-
-       /* Check for valid size. */
-       if (map->size < vma->vm_end - vma->vm_start)
-               return -EINVAL;
-
-       if (!capable(CAP_SYS_ADMIN) && (map->flags & _DRM_READ_ONLY)) {
-               vma->vm_flags &= ~(VM_WRITE | VM_MAYWRITE);
-#if defined(__i386__) || defined(__x86_64__)
-               pgprot_val(vma->vm_page_prot) &= ~_PAGE_RW;
-#else
-               /* Ye gads this is ugly.  With more thought
-                  we could move this up higher and use
-                  `protection_map' instead.  */
-               vma->vm_page_prot =
-                   __pgprot(pte_val
-                            (pte_wrprotect
-                             (__pte(pgprot_val(vma->vm_page_prot)))));
-#endif
-       }
-
-       switch (map->type) {
-#if !defined(__arm__)
-       case _DRM_AGP:
-               if (drm_core_has_AGP(dev) && dev->agp->cant_use_aperture) {
-                       /*
-                        * On some platforms we can't talk to bus dma address from the CPU, so for
-                        * memory of type DRM_AGP, we'll deal with sorting out the real physical
-                        * pages and mappings in fault()
-                        */
-#if defined(__powerpc__)
-                       pgprot_val(vma->vm_page_prot) |= _PAGE_NO_CACHE;
-#endif
-                       vma->vm_ops = &drm_vm_ops;
-                       break;
-               }
-               /* fall through to _DRM_FRAME_BUFFER... */
-#endif
-       case _DRM_FRAME_BUFFER:
-       case _DRM_REGISTERS:
-               offset = drm_core_get_reg_ofs(dev);
-               vma->vm_flags |= VM_IO; /* not in core dump */
-               vma->vm_page_prot = drm_io_prot(map->type, vma);
-#if !defined(__arm__)
-               if (io_remap_pfn_range(vma, vma->vm_start,
-                                      (map->offset + offset) >> PAGE_SHIFT,
-                                      vma->vm_end - vma->vm_start,
-                                      vma->vm_page_prot))
-                       return -EAGAIN;
-#else
-               if (remap_pfn_range(vma, vma->vm_start,
-                                       (map->offset + offset) >> PAGE_SHIFT,
-                                       vma->vm_end - vma->vm_start,
-                                       vma->vm_page_prot))
-                       return -EAGAIN;
-#endif
-
-               DRM_DEBUG("   Type = %d; start = 0x%lx, end = 0x%lx,"
-                         " offset = 0x%llx\n",
-                         map->type,
-                         vma->vm_start, vma->vm_end, (unsigned long long)(map->offset + offset));
-
-               vma->vm_ops = &drm_vm_ops;
-               break;
-       case _DRM_CONSISTENT:
-               /* Consistent memory is really like shared memory. But
-                * it's allocated in a different way, so avoid fault */
-               if (remap_pfn_range(vma, vma->vm_start,
-                   page_to_pfn(virt_to_page(map->handle)),
-                   vma->vm_end - vma->vm_start, vma->vm_page_prot))
-                       return -EAGAIN;
-               vma->vm_page_prot = drm_dma_prot(map->type, vma);
-       /* fall through to _DRM_SHM */
-       case _DRM_SHM:
-               vma->vm_ops = &drm_vm_shm_ops;
-               vma->vm_private_data = (void *)map;
-               /* Don't let this area swap.  Change when
-                  DRM_KERNEL advisory is supported. */
-               vma->vm_flags |= VM_RESERVED;
-               break;
-       case _DRM_SCATTER_GATHER:
-               vma->vm_ops = &drm_vm_sg_ops;
-               vma->vm_private_data = (void *)map;
-               vma->vm_flags |= VM_RESERVED;
-               vma->vm_page_prot = drm_dma_prot(map->type, vma);
-               break;
-       default:
-               return -EINVAL; /* This should never happen. */
-       }
-       vma->vm_flags |= VM_RESERVED;   /* Don't swap */
-       vma->vm_flags |= VM_DONTEXPAND;
-
-       vma->vm_file = filp;    /* Needed for drm_vm_open() */
-       drm_vm_open_locked(vma);
-       return 0;
-}
-
-int drm_mmap(struct file *filp, struct vm_area_struct *vma)
-{
-       struct drm_file *priv = filp->private_data;
-       struct drm_device *dev = priv->minor->dev;
-       int ret;
-
-       mutex_lock(&dev->struct_mutex);
-       ret = drm_mmap_locked(filp, vma);
-       mutex_unlock(&dev->struct_mutex);
-
-       return ret;
-}
-EXPORT_SYMBOL(drm_mmap);
index 70350fb..096f11f 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          DRM stub functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef        __PVR_DRM_MOD_H__
 #define        __PVR_DRM_MOD_H__
@@ -31,4 +46,4 @@ int drm_pvr_dev_add(void);
 
 void drm_pvr_dev_remove(void);
 
-#endif 
+#endif /* __PVR_DRM_MOD_H__ */
index 3a78d1e..ddbee9b 100644 (file)
@@ -1,33 +1,54 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          DRM stub functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+/*
+ * Emulate enough of the PCI layer to allow the Linux DRM module to be used
+ * with a non-PCI device.
+ * Only one device is supported at present.
+ */
 
 #include <linux/version.h>
 #include <linux/kernel.h>
-#include <linux/pci.h>
 #include <linux/module.h>
+#include <linux/pci.h>
 #include <asm/system.h>
 
 #include "pvr_drm_mod.h"
 
 #define        CLEAR_STRUCT(x) memset(&(x), 0, sizeof(x))
 
+/*
+ * Don't specify any initialisers for pvr_pci_bus and pvr_pci_dev, as they
+ * will be cleared to zero on unregister.  This has to be done for
+ * pvr_pci_dev to prevent a warning from the kernel if the device is
+ * re-registered without unloading the DRM module.
+ */
 static struct pci_bus pvr_pci_bus;
 static struct pci_dev pvr_pci_dev;
 
@@ -70,13 +97,13 @@ drm_pvr_dev_add(void)
                return 0;
        }
 
-       
+       /* Set the device ID */
        pvr_pci_dev.vendor = SGX_VENDOR_ID;
        pvr_pci_dev.device = SGX_DEVICE_ID;
        pvr_pci_dev.subsystem_vendor = SGX_SUB_VENDOR_ID;
        pvr_pci_dev.subsystem_device = SGX_SUB_DEVICE_ID;
 
-       
+       /* drm_set_busid needs the bus number */
        pvr_pci_dev.bus = &pvr_pci_bus;
 
        dev_set_name(&pvr_pci_dev.dev, "%s", "SGX");
@@ -106,7 +133,7 @@ drm_pvr_dev_remove(void)
                device_unregister(&pvr_pci_dev.dev);
                bDeviceIsRegistered = false;
 
-               
+               /* Prevent kernel warnings on re-register */
                CLEAR_STRUCT(pvr_pci_dev);
                CLEAR_STRUCT(pvr_pci_bus);
        }
index a7e9060..0ed1cad 100644 (file)
@@ -1,54 +1,70 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PowerVR drm driver shared definitions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #if !defined(__PVR_DRM_SHARED_H__)
 #define __PVR_DRM_SHARED_H__
 
 #if defined(SUPPORT_DRI_DRM)
 
+/* DRM command numbers, relative to DRM_COMMAND_BASE */
 #if defined(SUPPORT_DRI_DRM_EXT)
-#define PVR_DRM_SRVKM_CMD      DRM_PVR_RESERVED1       
-#define        PVR_DRM_DISP_CMD        DRM_PVR_RESERVED2       
-#define        PVR_DRM_BC_CMD          DRM_PVR_RESERVED3       
-#define PVR_DRM_IS_MASTER_CMD  DRM_PVR_RESERVED4       
-#define PVR_DRM_UNPRIV_CMD     DRM_PVR_RESERVED5       
-#define PVR_DRM_DBGDRV_CMD     DRM_PVR_RESERVED6       
-#else  
-#define PVR_DRM_SRVKM_CMD      0       
-#define        PVR_DRM_DISP_CMD        1       
-#define        PVR_DRM_BC_CMD          2       
-#define PVR_DRM_IS_MASTER_CMD  3       
-#define PVR_DRM_UNPRIV_CMD     4       
-#define PVR_DRM_DBGDRV_CMD     5       
-#endif 
-
-#define        PVR_DRM_UNPRIV_INIT_SUCCESFUL   0 
+#define PVR_DRM_SRVKM_CMD      DRM_PVR_RESERVED1       /* Used for PVR Services ioctls */
+#define        PVR_DRM_DISP_CMD        DRM_PVR_RESERVED2       /* Reserved for display class driver */
+#define        PVR_DRM_BC_CMD          DRM_PVR_RESERVED3       /* Reserved for buffer class driver */
+#define PVR_DRM_IS_MASTER_CMD  DRM_PVR_RESERVED4       /* Are we the DRM master? */
+#define PVR_DRM_UNPRIV_CMD     DRM_PVR_RESERVED5       /* PVR driver unprivileged ioctls */
+#define PVR_DRM_DBGDRV_CMD     DRM_PVR_RESERVED6       /* Debug driver (PDUMP) ioctls */
+#else  /* defined(SUPPORT_DRI_DRM_EXT) */
+#define PVR_DRM_SRVKM_CMD      0       /* Used for PVR Services ioctls */
+#define        PVR_DRM_DISP_CMD        1       /* Reserved for display class driver */
+#define        PVR_DRM_BC_CMD          2       /* Reserved for buffer class driver */
+#define PVR_DRM_IS_MASTER_CMD  3       /* Are we the DRM master? */
+#define PVR_DRM_UNPRIV_CMD     4       /* PVR driver unprivileged ioctls */
+#define PVR_DRM_DBGDRV_CMD     5       /* Debug driver (PDUMP) ioctls */
+#endif /* defined(SUPPORT_DRI_DRM_EXT) */
+
+/* Subcommands of PVR_DRM_UNPRIV_CMD */
+#define        PVR_DRM_UNPRIV_INIT_SUCCESFUL   0 /* PVR Services init succesful */
 
 #endif
 
-#endif 
+#endif /* defined(__PVR_DRM_SHARED_H__) */
 
 
index 4cd36d2..6d8aed5 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          buffer device class API structures and prototypes
+                for kernel services to kernel 3rd party buffer device driver
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description   provides display device class API structures and prototypes
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined (__KERNELBUFFER_H__)
 #define __KERNELBUFFER_H__
@@ -31,6 +48,9 @@
 extern "C" {
 #endif
 
+/*
+       Function table and pointers for SRVKM->BUFFER
+*/
 typedef PVRSRV_ERROR (*PFN_OPEN_BC_DEVICE)(IMG_UINT32, IMG_HANDLE*);
 typedef PVRSRV_ERROR (*PFN_CLOSE_BC_DEVICE)(IMG_UINT32, IMG_HANDLE);
 typedef PVRSRV_ERROR (*PFN_GET_BC_INFO)(IMG_HANDLE, BUFFER_INFO*);
@@ -48,6 +68,9 @@ typedef struct PVRSRV_BC_SRV2BUFFER_KMJTABLE_TAG
 } PVRSRV_BC_SRV2BUFFER_KMJTABLE;
 
 
+/*
+       Function table and pointers for BUFFER->SRVKM
+*/
 typedef PVRSRV_ERROR (*PFN_BC_REGISTER_BUFFER_DEV)(PVRSRV_BC_SRV2BUFFER_KMJTABLE*, IMG_UINT32*);
 typedef IMG_VOID (*PFN_BC_SCHEDULE_DEVICES)(IMG_VOID);
 typedef PVRSRV_ERROR (*PFN_BC_REMOVE_BUFFER_DEV)(IMG_UINT32);  
@@ -61,12 +84,14 @@ typedef struct PVRSRV_BC_BUFFER2SRV_KMJTABLE_TAG
 
 } PVRSRV_BC_BUFFER2SRV_KMJTABLE, *PPVRSRV_BC_BUFFER2SRV_KMJTABLE;
 
+/* function to retrieve kernel services function table from kernel services */
 typedef IMG_BOOL (*PFN_BC_GET_PVRJTABLE) (PPVRSRV_BC_BUFFER2SRV_KMJTABLE); 
 
+/* Prototype for platforms that access the JTable via linkage */
 IMG_IMPORT IMG_BOOL PVRGetBufferClassJTable(PVRSRV_BC_BUFFER2SRV_KMJTABLE *psJTable);
 
 #if defined (__cplusplus)
 }
 #endif
 
-#endif
+#endif/* #if !defined (__KERNELBUFFER_H__) */
index cdbef00..a99d5e7 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Display device class API structures and prototypes
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provides display device class API structures and prototypes
+                for kernel services to kernel 3rd party display.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined (__KERNELDISPLAY_H__)
 #define __KERNELDISPLAY_H__
@@ -65,10 +82,12 @@ typedef PVRSRV_ERROR (*PFN_SWAP_TO_DC_BUFFER)(IMG_HANDLE,
                                                                                          IMG_HANDLE,
                                                                                          IMG_UINT32,
                                                                                          IMG_RECT*);
-typedef PVRSRV_ERROR (*PFN_SWAP_TO_DC_SYSTEM)(IMG_HANDLE, IMG_HANDLE);
 typedef IMG_VOID (*PFN_QUERY_SWAP_COMMAND_ID)(IMG_HANDLE, IMG_HANDLE, IMG_HANDLE, IMG_HANDLE, IMG_UINT16*, IMG_BOOL*);
 typedef IMG_VOID (*PFN_SET_DC_STATE)(IMG_HANDLE, IMG_UINT32);
 
+/*
+       Function table for SRVKM->DISPLAY
+*/
 typedef struct PVRSRV_DC_SRV2DISP_KMJTABLE_TAG
 {
        IMG_UINT32                                              ui32TableSize;
@@ -87,14 +106,17 @@ typedef struct PVRSRV_DC_SRV2DISP_KMJTABLE_TAG
        PFN_SET_DC_SRCCK                                pfnSetDCSrcColourKey;
        PFN_GET_DC_BUFFERS                              pfnGetDCBuffers;
        PFN_SWAP_TO_DC_BUFFER                   pfnSwapToDCBuffer;
-       PFN_SWAP_TO_DC_SYSTEM                   pfnSwapToDCSystem;
        PFN_SET_DC_STATE                                pfnSetDCState;
        PFN_QUERY_SWAP_COMMAND_ID               pfnQuerySwapCommandID;
 
 } PVRSRV_DC_SRV2DISP_KMJTABLE;
 
+/* ISR callback pfn prototype */
 typedef IMG_BOOL (*PFN_ISR_HANDLER)(IMG_VOID*);
 
+/*
+       functions exported by kernel services for use by 3rd party kernel display class device driver
+*/
 typedef PVRSRV_ERROR (*PFN_DC_REGISTER_DISPLAY_DEV)(PVRSRV_DC_SRV2DISP_KMJTABLE*, IMG_UINT32*);
 typedef PVRSRV_ERROR (*PFN_DC_REMOVE_DISPLAY_DEV)(IMG_UINT32);
 typedef PVRSRV_ERROR (*PFN_DC_OEM_FUNCTION)(IMG_UINT32, IMG_VOID*, IMG_UINT32, IMG_VOID*, IMG_UINT32);
@@ -106,6 +128,16 @@ typedef PVRSRV_ERROR (*PFN_DC_REGISTER_POWER)(IMG_UINT32, PFN_PRE_POWER, PFN_POS
                                                                                          PFN_PRE_CLOCKSPEED_CHANGE, PFN_POST_CLOCKSPEED_CHANGE,
                                                                                          IMG_HANDLE, PVRSRV_DEV_POWER_STATE, PVRSRV_DEV_POWER_STATE);
 
+typedef struct _PVRSRV_KERNEL_MEM_INFO_* PDC_MEM_INFO;
+
+typedef PVRSRV_ERROR (*PFN_DC_MEMINFO_GET_CPU_VADDR)(PDC_MEM_INFO, IMG_CPU_VIRTADDR *pVAddr);
+typedef PVRSRV_ERROR (*PFN_DC_MEMINFO_GET_CPU_PADDR)(PDC_MEM_INFO, IMG_SIZE_T uByteOffset, IMG_CPU_PHYADDR *pPAddr);
+typedef PVRSRV_ERROR (*PFN_DC_MEMINFO_GET_BYTE_SIZE)(PDC_MEM_INFO, IMG_SIZE_T *uByteSize);
+typedef IMG_BOOL (*PFN_DC_MEMINFO_IS_PHYS_CONTIG)(PDC_MEM_INFO);
+
+/*
+       Function table for DISPLAY->SRVKM
+*/
 typedef struct PVRSRV_DC_DISP2SRV_KMJTABLE_TAG
 {
        IMG_UINT32                                              ui32TableSize;
@@ -118,42 +150,80 @@ typedef struct PVRSRV_DC_DISP2SRV_KMJTABLE_TAG
        PFN_DC_REGISTER_SYS_ISR                 pfnPVRSRVRegisterSystemISRHandler;
        PFN_DC_REGISTER_POWER                   pfnPVRSRVRegisterPowerDevice;
        PFN_DC_CMD_COMPLETE                             pfnPVRSRVFreeCmdCompletePacket;
+       PFN_DC_MEMINFO_GET_CPU_VADDR    pfnPVRSRVDCMemInfoGetCpuVAddr;
+       PFN_DC_MEMINFO_GET_CPU_PADDR    pfnPVRSRVDCMemInfoGetCpuPAddr;
+       PFN_DC_MEMINFO_GET_BYTE_SIZE    pfnPVRSRVDCMemInfoGetByteSize;
+       PFN_DC_MEMINFO_IS_PHYS_CONTIG   pfnPVRSRVDCMemInfoIsPhysContig;
+
 } PVRSRV_DC_DISP2SRV_KMJTABLE, *PPVRSRV_DC_DISP2SRV_KMJTABLE;
 
 
 typedef struct DISPLAYCLASS_FLIP_COMMAND_TAG
 {
-       
+       /* Ext Device Handle */
        IMG_HANDLE hExtDevice;
 
-       
+       /* Ext SwapChain Handle */
        IMG_HANDLE hExtSwapChain;
 
-       
+       /* Ext Buffer Handle (Buffer to Flip to) */
        IMG_HANDLE hExtBuffer;
 
-       
+       /* private tag */
        IMG_HANDLE hPrivateTag;
 
-       
+       /* number of clip rects */
        IMG_UINT32 ui32ClipRectCount;
 
-       
+       /* clip rects */
        IMG_RECT *psClipRect;
 
-       
+       /* number of vsync intervals between successive flips */
        IMG_UINT32      ui32SwapInterval;
 
 } DISPLAYCLASS_FLIP_COMMAND;
 
+
+typedef struct DISPLAYCLASS_FLIP_COMMAND2_TAG
+{
+       /* Ext Device Handle */
+       IMG_HANDLE hExtDevice;
+
+       /* Ext SwapChain Handle */
+       IMG_HANDLE hExtSwapChain;
+
+       /* Unused field, padding for compatibility with above structure */
+       IMG_HANDLE hUnused;
+
+       /* number of vsync intervals between successive flips */
+       IMG_UINT32 ui32SwapInterval;
+
+       /* private data from userspace */
+       IMG_PVOID  pvPrivData;
+
+       /* length of private data in bytes */
+       IMG_UINT32 ui32PrivDataLength;
+
+       /* meminfos */
+       PDC_MEM_INFO *ppsMemInfos;
+
+       /* number of meminfos */
+       IMG_UINT32 ui32NumMemInfos;
+
+} DISPLAYCLASS_FLIP_COMMAND2;
+
+/* start command IDs from 0 */
 #define DC_FLIP_COMMAND                0
 
+/* States used in PFN_SET_DC_STATE */
 #define DC_STATE_NO_FLUSH_COMMANDS             0
 #define DC_STATE_FLUSH_COMMANDS                        1
+#define DC_STATE_FORCE_SWAP_TO_SYSTEM  2
 
-
+/* function to retrieve kernel services function table from kernel services */
 typedef IMG_BOOL (*PFN_DC_GET_PVRJTABLE)(PPVRSRV_DC_DISP2SRV_KMJTABLE);
 
+/* Prototype for platforms that access the JTable via linkage */
 IMG_IMPORT IMG_BOOL PVRGetDisplayClassJTable(PVRSRV_DC_DISP2SRV_KMJTABLE *psJTable);
 
 
@@ -161,5 +231,8 @@ IMG_IMPORT IMG_BOOL PVRGetDisplayClassJTable(PVRSRV_DC_DISP2SRV_KMJTABLE *psJTab
 }
 #endif
 
-#endif
+#endif/* #if !defined (__KERNELDISPLAY_H__) */
 
+/******************************************************************************
+ End of file (kerneldisplay.h)
+******************************************************************************/
index c41a6d4..566a118 100644 (file)
@@ -1,29 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PDUMP flags definitions.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef _SERVICES_PDUMP_H_
 #define _SERVICES_PDUMP_H_
 
@@ -33,5 +47,5 @@
 #define PDUMP_FLAGS_CONTINUOUS         0x40000000U
 #define PDUMP_FLAGS_PERSISTENT         0x80000000U
 
-#endif 
+#endif /* _SERVICES_PDUMP_H_ */
 
index 74d2cc7..5a25467 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PVR Bridge Functionality
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Header for the PVR Bridge code
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __PVR_BRIDGE_H__
 #define __PVR_BRIDGE_H__
@@ -33,19 +49,24 @@ extern "C" {
 
 #include "servicesint.h"
 
+/*
+ * Bridge Cmd Ids
+ */
+
+
 #ifdef __linux__
 
                #include <linux/ioctl.h>
-    
+    /*!< Nov 2006: according to ioctl-number.txt 'g' wasn't in use. */
     #define PVRSRV_IOC_GID      'g'
     #define PVRSRV_IO(INDEX)    _IO(PVRSRV_IOC_GID, INDEX, PVRSRV_BRIDGE_PACKAGE)
     #define PVRSRV_IOW(INDEX)   _IOW(PVRSRV_IOC_GID, INDEX, PVRSRV_BRIDGE_PACKAGE)
     #define PVRSRV_IOR(INDEX)   _IOR(PVRSRV_IOC_GID, INDEX, PVRSRV_BRIDGE_PACKAGE)
     #define PVRSRV_IOWR(INDEX)  _IOWR(PVRSRV_IOC_GID, INDEX, PVRSRV_BRIDGE_PACKAGE)
 
-#else 
+#else /* __linux__ */
 
              #if defined(__QNXNTO__)
#if  defined(__QNXNTO__)
                        #define PVRSRV_IOC_GID      (0x0UL)
                #else
                        #error Unknown platform: Cannot define ioctls
@@ -57,26 +78,31 @@ extern "C" {
        #define PVRSRV_IOWR(INDEX)  (PVRSRV_IOC_GID + (INDEX))
 
        #define PVRSRV_BRIDGE_BASE                  PVRSRV_IOC_GID
-#endif 
+#endif /* __linux__ */
 
 
+/*
+ * Note *REMEMBER* to update PVRSRV_BRIDGE_LAST_CMD (below) if you add any new
+ * bridge commands!
+ */
+
 #define PVRSRV_BRIDGE_CORE_CMD_FIRST                   0UL
-#define PVRSRV_BRIDGE_ENUM_DEVICES                             PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+0)     
-#define PVRSRV_BRIDGE_ACQUIRE_DEVICEINFO               PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+1)     
-#define PVRSRV_BRIDGE_RELEASE_DEVICEINFO               PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+2)     
-#define PVRSRV_BRIDGE_CREATE_DEVMEMCONTEXT             PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+3)     
-#define PVRSRV_BRIDGE_DESTROY_DEVMEMCONTEXT            PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+4)     
-#define PVRSRV_BRIDGE_GET_DEVMEM_HEAPINFO              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+5)     
-#define PVRSRV_BRIDGE_ALLOC_DEVICEMEM                  PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+6)     
-#define PVRSRV_BRIDGE_FREE_DEVICEMEM                   PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+7)     
-#define PVRSRV_BRIDGE_GETFREE_DEVICEMEM                        PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+8)     
-#define PVRSRV_BRIDGE_CREATE_COMMANDQUEUE              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+9)     
-#define PVRSRV_BRIDGE_DESTROY_COMMANDQUEUE             PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+10)    
-#define        PVRSRV_BRIDGE_MHANDLE_TO_MMAP_DATA              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+11)   
-#define PVRSRV_BRIDGE_CONNECT_SERVICES                 PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+12)    
-#define PVRSRV_BRIDGE_DISCONNECT_SERVICES              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+13)    
-#define PVRSRV_BRIDGE_WRAP_DEVICE_MEM                  PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+14)    
-#define PVRSRV_BRIDGE_GET_DEVICEMEMINFO                        PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+15)    
+#define PVRSRV_BRIDGE_ENUM_DEVICES                             PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+0)     /*!< enumerate device bridge index */
+#define PVRSRV_BRIDGE_ACQUIRE_DEVICEINFO               PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+1)     /*!< acquire device data bridge index */
+#define PVRSRV_BRIDGE_RELEASE_DEVICEINFO               PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+2)     /*!< release device data bridge index */
+#define PVRSRV_BRIDGE_CREATE_DEVMEMCONTEXT             PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+3)     /*!< create device addressable memory context */
+#define PVRSRV_BRIDGE_DESTROY_DEVMEMCONTEXT            PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+4)     /*!< destroy device addressable memory context */
+#define PVRSRV_BRIDGE_GET_DEVMEM_HEAPINFO              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+5)     /*!< get device memory heap info */
+#define PVRSRV_BRIDGE_ALLOC_DEVICEMEM                  PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+6)     /*!< alloc device memory bridge index */
+#define PVRSRV_BRIDGE_FREE_DEVICEMEM                   PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+7)     /*!< free device memory bridge index */
+#define PVRSRV_BRIDGE_GETFREE_DEVICEMEM                        PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+8)     /*!< get free device memory bridge index */
+#define PVRSRV_BRIDGE_CREATE_COMMANDQUEUE              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+9)     /*!< create Cmd Q bridge index */
+#define PVRSRV_BRIDGE_DESTROY_COMMANDQUEUE             PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+10)    /*!< destroy Cmd Q bridge index */
+#define        PVRSRV_BRIDGE_MHANDLE_TO_MMAP_DATA              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+11)   /*!< generate mmap data from a memory handle */
+#define PVRSRV_BRIDGE_CONNECT_SERVICES                 PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+12)    /*!< services connect bridge index */
+#define PVRSRV_BRIDGE_DISCONNECT_SERVICES              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+13)    /*!< services disconnect bridge index */
+#define PVRSRV_BRIDGE_WRAP_DEVICE_MEM                  PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+14)    /*!< wrap device memory bridge index */
+#define PVRSRV_BRIDGE_GET_DEVICEMEMINFO                        PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+15)    /*!< read the kernel meminfo record */
 #define PVRSRV_BRIDGE_RESERVE_DEV_VIRTMEM              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+16)
 #define PVRSRV_BRIDGE_FREE_DEV_VIRTMEM                 PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+17)
 #define PVRSRV_BRIDGE_MAP_EXT_MEMORY                   PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+18)
@@ -92,71 +118,88 @@ extern "C" {
 #define PVRSRV_BRIDGE_CHG_DEV_MEM_ATTRIBS              PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+28)
 #define PVRSRV_BRIDGE_MAP_DEV_MEMORY_2                 PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+29)
 #define PVRSRV_BRIDGE_EXPORT_DEVICEMEM_2               PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+30)
+#if defined (SUPPORT_ION)
+#define PVRSRV_BRIDGE_MAP_ION_HANDLE                   PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+31)
+#define PVRSRV_BRIDGE_UNMAP_ION_HANDLE                 PVRSRV_IOWR(PVRSRV_BRIDGE_CORE_CMD_FIRST+32)
+#define PVRSRV_BRIDGE_CORE_CMD_LAST                            (PVRSRV_BRIDGE_CORE_CMD_FIRST+32)
+#else
 #define PVRSRV_BRIDGE_CORE_CMD_LAST                            (PVRSRV_BRIDGE_CORE_CMD_FIRST+30)
-
+#endif
+/* SIM */
 #define PVRSRV_BRIDGE_SIM_CMD_FIRST                            (PVRSRV_BRIDGE_CORE_CMD_LAST+1)
-#define PVRSRV_BRIDGE_PROCESS_SIMISR_EVENT             PVRSRV_IOWR(PVRSRV_BRIDGE_SIM_CMD_FIRST+0)      
-#define PVRSRV_BRIDGE_REGISTER_SIM_PROCESS             PVRSRV_IOWR(PVRSRV_BRIDGE_SIM_CMD_FIRST+1)      
-#define PVRSRV_BRIDGE_UNREGISTER_SIM_PROCESS   PVRSRV_IOWR(PVRSRV_BRIDGE_SIM_CMD_FIRST+2)      
+#define PVRSRV_BRIDGE_PROCESS_SIMISR_EVENT             PVRSRV_IOWR(PVRSRV_BRIDGE_SIM_CMD_FIRST+0)      /*!< RTSIM pseudo ISR */
+#define PVRSRV_BRIDGE_REGISTER_SIM_PROCESS             PVRSRV_IOWR(PVRSRV_BRIDGE_SIM_CMD_FIRST+1)      /*!< Register RTSIM process thread */
+#define PVRSRV_BRIDGE_UNREGISTER_SIM_PROCESS   PVRSRV_IOWR(PVRSRV_BRIDGE_SIM_CMD_FIRST+2)      /*!< Unregister RTSIM process thread */
 #define PVRSRV_BRIDGE_SIM_CMD_LAST                             (PVRSRV_BRIDGE_SIM_CMD_FIRST+2)
 
+/* User Mapping */
 #define PVRSRV_BRIDGE_MAPPING_CMD_FIRST                        (PVRSRV_BRIDGE_SIM_CMD_LAST+1)
-#define PVRSRV_BRIDGE_MAPPHYSTOUSERSPACE               PVRSRV_IOWR(PVRSRV_BRIDGE_MAPPING_CMD_FIRST+0)  
-#define PVRSRV_BRIDGE_UNMAPPHYSTOUSERSPACE             PVRSRV_IOWR(PVRSRV_BRIDGE_MAPPING_CMD_FIRST+1)  
-#define PVRSRV_BRIDGE_GETPHYSTOUSERSPACEMAP            PVRSRV_IOWR(PVRSRV_BRIDGE_MAPPING_CMD_FIRST+2)  
+#define PVRSRV_BRIDGE_MAPPHYSTOUSERSPACE               PVRSRV_IOWR(PVRSRV_BRIDGE_MAPPING_CMD_FIRST+0)  /*!< map CPU phys to user space */
+#define PVRSRV_BRIDGE_UNMAPPHYSTOUSERSPACE             PVRSRV_IOWR(PVRSRV_BRIDGE_MAPPING_CMD_FIRST+1)  /*!< unmap CPU phys to user space */
+#define PVRSRV_BRIDGE_GETPHYSTOUSERSPACEMAP            PVRSRV_IOWR(PVRSRV_BRIDGE_MAPPING_CMD_FIRST+2)  /*!< get user copy of Phys to Lin loopup table */
 #define PVRSRV_BRIDGE_MAPPING_CMD_LAST                 (PVRSRV_BRIDGE_MAPPING_CMD_FIRST+2)
 
 #define PVRSRV_BRIDGE_STATS_CMD_FIRST                  (PVRSRV_BRIDGE_MAPPING_CMD_LAST+1)
-#define        PVRSRV_BRIDGE_GET_FB_STATS                              PVRSRV_IOWR(PVRSRV_BRIDGE_STATS_CMD_FIRST+0)    
+#define        PVRSRV_BRIDGE_GET_FB_STATS                              PVRSRV_IOWR(PVRSRV_BRIDGE_STATS_CMD_FIRST+0)    /*!< Get FB memory stats */
 #define PVRSRV_BRIDGE_STATS_CMD_LAST                   (PVRSRV_BRIDGE_STATS_CMD_FIRST+0)
 
+/* API to retrieve misc. info. from services */
 #define PVRSRV_BRIDGE_MISC_CMD_FIRST                   (PVRSRV_BRIDGE_STATS_CMD_LAST+1)
-#define PVRSRV_BRIDGE_GET_MISC_INFO                            PVRSRV_IOWR(PVRSRV_BRIDGE_MISC_CMD_FIRST+0)     
-#define PVRSRV_BRIDGE_RELEASE_MISC_INFO                        PVRSRV_IOWR(PVRSRV_BRIDGE_MISC_CMD_FIRST+1)     
+#define PVRSRV_BRIDGE_GET_MISC_INFO                            PVRSRV_IOWR(PVRSRV_BRIDGE_MISC_CMD_FIRST+0)     /*!< misc. info. */
+#define PVRSRV_BRIDGE_RELEASE_MISC_INFO                        PVRSRV_IOWR(PVRSRV_BRIDGE_MISC_CMD_FIRST+1)     /*!< misc. info. */
 #define PVRSRV_BRIDGE_MISC_CMD_LAST                            (PVRSRV_BRIDGE_MISC_CMD_FIRST+1)
 
+/* Overlay ioctls */
+
 #if defined (SUPPORT_OVERLAY_ROTATE_BLIT)
 #define PVRSRV_BRIDGE_OVERLAY_CMD_FIRST                        (PVRSRV_BRIDGE_MISC_CMD_LAST+1)
-#define PVRSRV_BRIDGE_INIT_3D_OVL_BLT_RES              PVRSRV_IOWR(PVRSRV_BRIDGE_OVERLAY_CMD_FIRST+0)  
-#define PVRSRV_BRIDGE_DEINIT_3D_OVL_BLT_RES            PVRSRV_IOWR(PVRSRV_BRIDGE_OVERLAY_CMD_FIRST+1)  
+#define PVRSRV_BRIDGE_INIT_3D_OVL_BLT_RES              PVRSRV_IOWR(PVRSRV_BRIDGE_OVERLAY_CMD_FIRST+0)  /*!< 3D Overlay rotate blit init */
+#define PVRSRV_BRIDGE_DEINIT_3D_OVL_BLT_RES            PVRSRV_IOWR(PVRSRV_BRIDGE_OVERLAY_CMD_FIRST+1)  /*!< 3D Overlay rotate blit deinit */
 #define PVRSRV_BRIDGE_OVERLAY_CMD_LAST                 (PVRSRV_BRIDGE_OVERLAY_CMD_FIRST+1)
 #else
 #define PVRSRV_BRIDGE_OVERLAY_CMD_LAST                 PVRSRV_BRIDGE_MISC_CMD_LAST
 #endif
 
+/* PDUMP */
 #if defined(PDUMP)
 #define PVRSRV_BRIDGE_PDUMP_CMD_FIRST                  (PVRSRV_BRIDGE_OVERLAY_CMD_LAST+1)
-#define PVRSRV_BRIDGE_PDUMP_INIT                       PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+0)    
-#define PVRSRV_BRIDGE_PDUMP_MEMPOL                     PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+1)    
-#define PVRSRV_BRIDGE_PDUMP_DUMPMEM                    PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+2)    
-#define PVRSRV_BRIDGE_PDUMP_REG                                PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+3)    
-#define PVRSRV_BRIDGE_PDUMP_REGPOL                     PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+4)    
-#define PVRSRV_BRIDGE_PDUMP_COMMENT                    PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+5)    
-#define PVRSRV_BRIDGE_PDUMP_SETFRAME                   PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+6)    
-#define PVRSRV_BRIDGE_PDUMP_ISCAPTURING                        PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+7)    
-#define PVRSRV_BRIDGE_PDUMP_DUMPBITMAP                 PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+8)    
-#define PVRSRV_BRIDGE_PDUMP_DUMPREADREG                        PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+9)    
-#define PVRSRV_BRIDGE_PDUMP_SYNCPOL                    PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+10)   
-#define PVRSRV_BRIDGE_PDUMP_DUMPSYNC                   PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+11)   
-#define PVRSRV_BRIDGE_PDUMP_MEMPAGES                   PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+12)   
-#define PVRSRV_BRIDGE_PDUMP_DRIVERINFO                 PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+13)   
-#define PVRSRV_BRIDGE_PDUMP_DUMPPDDEVPADDR             PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+15)   
+#define PVRSRV_BRIDGE_PDUMP_INIT                       PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+0)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_MEMPOL                     PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+1)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_DUMPMEM                    PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+2)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_REG                                PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+3)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_REGPOL                     PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+4)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_COMMENT                    PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+5)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_SETFRAME                   PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+6)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_ISCAPTURING                        PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+7)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_DUMPBITMAP                 PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+8)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_DUMPREADREG                        PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+9)    /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_SYNCPOL                    PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+10)   /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_DUMPSYNC                   PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+11)   /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_MEMPAGES                   PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+12)   /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_DRIVERINFO                 PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+13)   /*!< pdump command structure */
+#define PVRSRV_BRIDGE_PDUMP_DUMPPDDEVPADDR             PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+15)   /*!< pdump command structure */
 #define PVRSRV_BRIDGE_PDUMP_CYCLE_COUNT_REG_READ       PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+16)
 #define PVRSRV_BRIDGE_PDUMP_STARTINITPHASE                     PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+17)
 #define PVRSRV_BRIDGE_PDUMP_STOPINITPHASE                      PVRSRV_IOWR(PVRSRV_BRIDGE_PDUMP_CMD_FIRST+18)
 #define PVRSRV_BRIDGE_PDUMP_CMD_LAST                   (PVRSRV_BRIDGE_PDUMP_CMD_FIRST+18)
 #else
+/* Note we are carefull here not to leave a large gap in the ioctl numbers.
+ * (Some ports may use these values to index into an array where large gaps can
+ * waste memory) */
 #define PVRSRV_BRIDGE_PDUMP_CMD_LAST                   PVRSRV_BRIDGE_OVERLAY_CMD_LAST
 #endif
 
+/* DisplayClass APIs */
 #define PVRSRV_BRIDGE_OEM_CMD_FIRST                            (PVRSRV_BRIDGE_PDUMP_CMD_LAST+1)
-#define PVRSRV_BRIDGE_GET_OEMJTABLE                            PVRSRV_IOWR(PVRSRV_BRIDGE_OEM_CMD_FIRST+0)      
+#define PVRSRV_BRIDGE_GET_OEMJTABLE                            PVRSRV_IOWR(PVRSRV_BRIDGE_OEM_CMD_FIRST+0)      /*!< Get OEM Jtable */
 #define PVRSRV_BRIDGE_OEM_CMD_LAST                             (PVRSRV_BRIDGE_OEM_CMD_FIRST+0)
 
+/* device class enum */
 #define PVRSRV_BRIDGE_DEVCLASS_CMD_FIRST               (PVRSRV_BRIDGE_OEM_CMD_LAST+1)
 #define PVRSRV_BRIDGE_ENUM_CLASS                               PVRSRV_IOWR(PVRSRV_BRIDGE_DEVCLASS_CMD_FIRST+0)
 #define PVRSRV_BRIDGE_DEVCLASS_CMD_LAST                        (PVRSRV_BRIDGE_DEVCLASS_CMD_FIRST+0)
 
+/* display class API */
 #define PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST              (PVRSRV_BRIDGE_DEVCLASS_CMD_LAST+1)
 #define PVRSRV_BRIDGE_OPEN_DISPCLASS_DEVICE            PVRSRV_IOWR(PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+0)
 #define PVRSRV_BRIDGE_CLOSE_DISPCLASS_DEVICE   PVRSRV_IOWR(PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+1)
@@ -172,9 +215,11 @@ extern "C" {
 #define PVRSRV_BRIDGE_SET_DISPCLASS_SRCCOLOURKEY               PVRSRV_IOWR(PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+11)
 #define PVRSRV_BRIDGE_GET_DISPCLASS_BUFFERS            PVRSRV_IOWR(PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+12)
 #define PVRSRV_BRIDGE_SWAP_DISPCLASS_TO_BUFFER PVRSRV_IOWR(PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+13)
-#define PVRSRV_BRIDGE_SWAP_DISPCLASS_TO_SYSTEM PVRSRV_IOWR(PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+14)
-#define PVRSRV_BRIDGE_DISPCLASS_CMD_LAST               (PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+14)
+#define PVRSRV_BRIDGE_SWAP_DISPCLASS_TO_BUFFER2        PVRSRV_IOWR(PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+14)
+#define PVRSRV_BRIDGE_SWAP_DISPCLASS_TO_SYSTEM PVRSRV_IOWR(PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+15)
+#define PVRSRV_BRIDGE_DISPCLASS_CMD_LAST               (PVRSRV_BRIDGE_DISPCLASS_CMD_FIRST+15)
 
+/* buffer class API */
 #define PVRSRV_BRIDGE_BUFCLASS_CMD_FIRST               (PVRSRV_BRIDGE_DISPCLASS_CMD_LAST+1)
 #define PVRSRV_BRIDGE_OPEN_BUFFERCLASS_DEVICE  PVRSRV_IOWR(PVRSRV_BRIDGE_BUFCLASS_CMD_FIRST+0)
 #define PVRSRV_BRIDGE_CLOSE_BUFFERCLASS_DEVICE PVRSRV_IOWR(PVRSRV_BRIDGE_BUFCLASS_CMD_FIRST+1)
@@ -182,11 +227,13 @@ extern "C" {
 #define PVRSRV_BRIDGE_GET_BUFFERCLASS_BUFFER   PVRSRV_IOWR(PVRSRV_BRIDGE_BUFCLASS_CMD_FIRST+3)
 #define PVRSRV_BRIDGE_BUFCLASS_CMD_LAST                        (PVRSRV_BRIDGE_BUFCLASS_CMD_FIRST+3)
 
+/* Wrap/Unwrap external memory */
 #define PVRSRV_BRIDGE_WRAP_CMD_FIRST                   (PVRSRV_BRIDGE_BUFCLASS_CMD_LAST+1)
 #define PVRSRV_BRIDGE_WRAP_EXT_MEMORY                  PVRSRV_IOWR(PVRSRV_BRIDGE_WRAP_CMD_FIRST+0)
 #define PVRSRV_BRIDGE_UNWRAP_EXT_MEMORY                        PVRSRV_IOWR(PVRSRV_BRIDGE_WRAP_CMD_FIRST+1)
 #define PVRSRV_BRIDGE_WRAP_CMD_LAST                            (PVRSRV_BRIDGE_WRAP_CMD_FIRST+1)
 
+/* Shared memory */
 #define PVRSRV_BRIDGE_SHAREDMEM_CMD_FIRST              (PVRSRV_BRIDGE_WRAP_CMD_LAST+1)
 #define PVRSRV_BRIDGE_ALLOC_SHARED_SYS_MEM             PVRSRV_IOWR(PVRSRV_BRIDGE_SHAREDMEM_CMD_FIRST+0)
 #define PVRSRV_BRIDGE_FREE_SHARED_SYS_MEM              PVRSRV_IOWR(PVRSRV_BRIDGE_SHAREDMEM_CMD_FIRST+1)
@@ -194,17 +241,20 @@ extern "C" {
 #define PVRSRV_BRIDGE_UNMAP_MEMINFO_MEM                        PVRSRV_IOWR(PVRSRV_BRIDGE_SHAREDMEM_CMD_FIRST+3)
 #define PVRSRV_BRIDGE_SHAREDMEM_CMD_LAST               (PVRSRV_BRIDGE_SHAREDMEM_CMD_FIRST+3)
 
+/* Intialisation Service support */
 #define PVRSRV_BRIDGE_INITSRV_CMD_FIRST                        (PVRSRV_BRIDGE_SHAREDMEM_CMD_LAST+1)
 #define PVRSRV_BRIDGE_INITSRV_CONNECT                  PVRSRV_IOWR(PVRSRV_BRIDGE_INITSRV_CMD_FIRST+0)
 #define PVRSRV_BRIDGE_INITSRV_DISCONNECT               PVRSRV_IOWR(PVRSRV_BRIDGE_INITSRV_CMD_FIRST+1)
 #define PVRSRV_BRIDGE_INITSRV_CMD_LAST                 (PVRSRV_BRIDGE_INITSRV_CMD_FIRST+1)
 
+/* Event Objects */
 #define PVRSRV_BRIDGE_EVENT_OBJECT_CMD_FIRST   (PVRSRV_BRIDGE_INITSRV_CMD_LAST+1)
 #define PVRSRV_BRIDGE_EVENT_OBJECT_WAIT                        PVRSRV_IOWR(PVRSRV_BRIDGE_EVENT_OBJECT_CMD_FIRST+0)
 #define PVRSRV_BRIDGE_EVENT_OBJECT_OPEN                        PVRSRV_IOWR(PVRSRV_BRIDGE_EVENT_OBJECT_CMD_FIRST+1)
 #define PVRSRV_BRIDGE_EVENT_OBJECT_CLOSE               PVRSRV_IOWR(PVRSRV_BRIDGE_EVENT_OBJECT_CMD_FIRST+2)
 #define PVRSRV_BRIDGE_EVENT_OBJECT_CMD_LAST            (PVRSRV_BRIDGE_EVENT_OBJECT_CMD_FIRST+2)
 
+/* Sync ops */
 #define PVRSRV_BRIDGE_SYNC_OPS_CMD_FIRST               (PVRSRV_BRIDGE_EVENT_OBJECT_CMD_LAST+1)
 #define PVRSRV_BRIDGE_CREATE_SYNC_INFO_MOD_OBJ PVRSRV_IOWR(PVRSRV_BRIDGE_SYNC_OPS_CMD_FIRST+0)
 #define PVRSRV_BRIDGE_DESTROY_SYNC_INFO_MOD_OBJ        PVRSRV_IOWR(PVRSRV_BRIDGE_SYNC_OPS_CMD_FIRST+1)
@@ -218,11 +268,22 @@ extern "C" {
 #define PVRSRV_BRIDGE_FREE_SYNC_INFO            PVRSRV_IOWR(PVRSRV_BRIDGE_SYNC_OPS_CMD_FIRST+9)
 #define PVRSRV_BRIDGE_SYNC_OPS_CMD_LAST                        (PVRSRV_BRIDGE_SYNC_OPS_CMD_FIRST+9)
 
+/* For sgx_bridge.h (msvdx_bridge.h should probably use these defines too) */
 #define PVRSRV_BRIDGE_LAST_NON_DEVICE_CMD              (PVRSRV_BRIDGE_SYNC_OPS_CMD_LAST+1)
 
 
+/******************************************************************************
+ * Bridge flags
+ *****************************************************************************/
 #define PVRSRV_KERNEL_MODE_CLIENT                              1
 
+/******************************************************************************
+ * Generic bridge structures
+ *****************************************************************************/
+
+/******************************************************************************
+ *     bridge return structure
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_RETURN_TAG
 {
        PVRSRV_ERROR eError;
@@ -231,48 +292,68 @@ typedef struct PVRSRV_BRIDGE_RETURN_TAG
 }PVRSRV_BRIDGE_RETURN;
 
 
+/******************************************************************************
+ *     bridge packaging structure
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_PACKAGE_TAG
 {
-       IMG_UINT32                              ui32BridgeID;                   
-       IMG_UINT32                              ui32Size;                               
-       IMG_VOID                                *pvParamIn;                             
-       IMG_UINT32                              ui32InBufferSize;               
-       IMG_VOID                                *pvParamOut;                    
-       IMG_UINT32                              ui32OutBufferSize;              
+       IMG_UINT32                              ui32BridgeID;                   /*!< ioctl/drvesc index */
+       IMG_UINT32                              ui32Size;                               /*!< size of structure */
+       IMG_VOID                                *pvParamIn;                             /*!< input data buffer */
+       IMG_UINT32                              ui32InBufferSize;               /*!< size of input data buffer */
+       IMG_VOID                                *pvParamOut;                    /*!< output data buffer */
+       IMG_UINT32                              ui32OutBufferSize;              /*!< size of output data buffer */
 
 #if defined (SUPPORT_SID_INTERFACE)
-       IMG_SID                                 hKernelServices;                
+       IMG_SID                                 hKernelServices;                /*!< kernel servcies handle */
 #else
-       IMG_HANDLE                              hKernelServices;                
+       IMG_HANDLE                              hKernelServices;                /*!< kernel servcies handle */
 #endif
 }PVRSRV_BRIDGE_PACKAGE;
 
 
+/******************************************************************************
+ * Input structures for IOCTL/DRVESC
+ *****************************************************************************/
+
+
+/******************************************************************************
+ *     'bridge in' connect to services
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_CONNECT_SERVICES_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
        IMG_UINT32              ui32Flags;
 } PVRSRV_BRIDGE_IN_CONNECT_SERVICES;
 
+/******************************************************************************
+ *     'bridge in' acquire device info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_ACQUIRE_DEVICEINFO_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        IMG_UINT32                      uiDevIndex;
        PVRSRV_DEVICE_TYPE      eDeviceType;
 
 } PVRSRV_BRIDGE_IN_ACQUIRE_DEVICEINFO;
 
 
+/******************************************************************************
+ *     'bridge in' enum class
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_ENUMCLASS_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        PVRSRV_DEVICE_CLASS sDeviceClass;
 } PVRSRV_BRIDGE_IN_ENUMCLASS;
 
 
+/******************************************************************************
+ *     'bridge in' close display class device
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_CLOSE_DISPCLASS_DEVICE_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDeviceKM;
 #else
@@ -281,9 +362,12 @@ typedef struct PVRSRV_BRIDGE_IN_CLOSE_DISPCLASS_DEVICE_TAG
 } PVRSRV_BRIDGE_IN_CLOSE_DISPCLASS_DEVICE;
 
 
+/******************************************************************************
+ *     'bridge in' enum display class formats
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_ENUM_DISPCLASS_FORMATS_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDeviceKM;
 #else
@@ -292,9 +376,12 @@ typedef struct PVRSRV_BRIDGE_IN_ENUM_DISPCLASS_FORMATS_TAG
 } PVRSRV_BRIDGE_IN_ENUM_DISPCLASS_FORMATS;
 
 
+/******************************************************************************
+ *     'bridge in' get display class sysbuffer
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GET_DISPCLASS_SYSBUFFER_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDeviceKM;
 #else
@@ -303,9 +390,12 @@ typedef struct PVRSRV_BRIDGE_IN_GET_DISPCLASS_SYSBUFFER_TAG
 } PVRSRV_BRIDGE_IN_GET_DISPCLASS_SYSBUFFER;
 
 
+/******************************************************************************
+ *     'bridge in' display class info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GET_DISPCLASS_INFO_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDeviceKM;
 #else
@@ -314,9 +404,12 @@ typedef struct PVRSRV_BRIDGE_IN_GET_DISPCLASS_INFO_TAG
 } PVRSRV_BRIDGE_IN_GET_DISPCLASS_INFO;
 
 
+/******************************************************************************
+ *     'bridge in' close buffer class device
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_CLOSE_BUFFERCLASS_DEVICE_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDeviceKM;
 #else
@@ -325,9 +418,12 @@ typedef struct PVRSRV_BRIDGE_IN_CLOSE_BUFFERCLASS_DEVICE_TAG
 } PVRSRV_BRIDGE_IN_CLOSE_BUFFERCLASS_DEVICE;
 
 
+/******************************************************************************
+ *     'bridge in' close buffer class device
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GET_BUFFERCLASS_INFO_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDeviceKM;
 #else
@@ -336,9 +432,12 @@ typedef struct PVRSRV_BRIDGE_IN_GET_BUFFERCLASS_INFO_TAG
 } PVRSRV_BRIDGE_IN_GET_BUFFERCLASS_INFO;
 
 
+/******************************************************************************
+ *     'bridge out' acquire device info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_RELEASE_DEVICEINFO_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
 #else
@@ -348,18 +447,24 @@ typedef struct PVRSRV_BRIDGE_IN_RELEASE_DEVICEINFO_TAG
 } PVRSRV_BRIDGE_IN_RELEASE_DEVICEINFO;
 
 
+/******************************************************************************
+ *     'bridge in' free class devices info.
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_FREE_CLASSDEVICEINFO_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        PVRSRV_DEVICE_CLASS DeviceClass;
        IMG_VOID*                       pvDevInfo;
 
 }PVRSRV_BRIDGE_IN_FREE_CLASSDEVICEINFO;
 
 
+/******************************************************************************
+ *     'bridge in' get device memory heap info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GET_DEVMEM_HEAPINFO_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
        IMG_SID                         hDevMemContext;
@@ -371,9 +476,12 @@ typedef struct PVRSRV_BRIDGE_IN_GET_DEVMEM_HEAPINFO_TAG
 }PVRSRV_BRIDGE_IN_GET_DEVMEM_HEAPINFO;
 
 
+/******************************************************************************
+ *     'bridge in' create device memory context
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_CREATE_DEVMEMCONTEXT_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
 #else
@@ -383,9 +491,12 @@ typedef struct PVRSRV_BRIDGE_IN_CREATE_DEVMEMCONTEXT_TAG
 }PVRSRV_BRIDGE_IN_CREATE_DEVMEMCONTEXT;
 
 
+/******************************************************************************
+ *     'bridge in' destroy device memory context
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_DESTROY_DEVMEMCONTEXT_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
        IMG_SID                         hDevMemContext;
@@ -397,9 +508,12 @@ typedef struct PVRSRV_BRIDGE_IN_DESTROY_DEVMEMCONTEXT_TAG
 }PVRSRV_BRIDGE_IN_DESTROY_DEVMEMCONTEXT;
 
 
+/******************************************************************************
+ *     'bridge in' alloc device memory
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_ALLOCDEVICEMEM_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
        IMG_SID                         hDevMemHeap;
@@ -410,12 +524,21 @@ typedef struct PVRSRV_BRIDGE_IN_ALLOCDEVICEMEM_TAG
        IMG_UINT32                      ui32Attribs;
        IMG_SIZE_T                      ui32Size;
        IMG_SIZE_T                      ui32Alignment;
+       IMG_PVOID                       pvPrivData;
+       IMG_UINT32                      ui32PrivDataLength;
 
+       IMG_UINT32                      ui32ChunkSize;
+       IMG_UINT32                      ui32NumVirtChunks;
+       IMG_UINT32                      ui32NumPhysChunks;
+       IMG_BOOL                        *pabMapChunk;
 }PVRSRV_BRIDGE_IN_ALLOCDEVICEMEM;
 
+/******************************************************************************
+ *     'bridge in' map meminfo to user mode
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_MAPMEMINFOTOUSER_TAG
 {
-       IMG_UINT32  ui32BridgeFlags; 
+       IMG_UINT32  ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID     hKernelMemInfo;
 #else
@@ -424,9 +547,12 @@ typedef struct PVRSRV_BRIDGE_IN_MAPMEMINFOTOUSER_TAG
 
 }PVRSRV_BRIDGE_IN_MAPMEMINFOTOUSER;
 
+/******************************************************************************
+ *     'bridge in' unmap meminfo from user mode
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_UNMAPMEMINFOFROMUSER_TAG
 {
-       IMG_UINT32      ui32BridgeFlags; 
+       IMG_UINT32      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID         hKernelMemInfo;
 #else
@@ -441,9 +567,12 @@ typedef struct PVRSRV_BRIDGE_IN_UNMAPMEMINFOFROMUSER_TAG
 
 }PVRSRV_BRIDGE_IN_UNMAPMEMINFOFROMUSER;
 
+/******************************************************************************
+ *     'bridge in' free device memory
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_FREEDEVICEMEM_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDevCookie;
        IMG_SID                 hKernelMemInfo;
@@ -455,9 +584,12 @@ typedef struct PVRSRV_BRIDGE_IN_FREEDEVICEMEM_TAG
 
 }PVRSRV_BRIDGE_IN_FREEDEVICEMEM;
 
+/******************************************************************************
+ *     'bridge in' export device memory
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_EXPORTDEVICEMEM_TAG
 {
-       IMG_UINT32      ui32BridgeFlags; 
+       IMG_UINT32      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID         hDevCookie;
        IMG_SID         hKernelMemInfo;
@@ -468,16 +600,53 @@ typedef struct PVRSRV_BRIDGE_IN_EXPORTDEVICEMEM_TAG
 
 }PVRSRV_BRIDGE_IN_EXPORTDEVICEMEM;
 
+/******************************************************************************
+ *     'bridge in' map ion handle
+ *****************************************************************************/
+typedef struct _PVRSRV_BRIDGE_IN_MAP_ION_HANDLE_
+{
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
+       IMG_HANDLE                      handle;
+       IMG_UINT32                      ui32Attribs;
+       IMG_SIZE_T                      ui32Size;
+#if defined (SUPPORT_SID_INTERFACE)
+       IMG_SID                         hDevCookie;
+       IMG_SID                         hDevMemContext;
+#else
+       IMG_HANDLE                      hDevCookie;
+       IMG_HANDLE                      hDevMemContext;
+#endif
+} PVRSRV_BRIDGE_IN_MAP_ION_HANDLE;
+
+/******************************************************************************
+ *     'bridge in' unmap ion handle
+ *****************************************************************************/
+typedef struct PVRSRV_BRIDGE_IN_UNMAP_ION_HANDLE_TAG
+{
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
+#if defined (SUPPORT_SID_INTERFACE)
+       IMG_SID                 hKernelMemInfo;
+#else
+       PVRSRV_KERNEL_MEM_INFO  *psKernelMemInfo;
+#endif
+}PVRSRV_BRIDGE_IN_UNMAP_ION_HANDLE;
+
+/******************************************************************************
+ *     'bridge in' get free device memory
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GETFREEDEVICEMEM_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        IMG_UINT32                      ui32Flags;
 
 } PVRSRV_BRIDGE_IN_GETFREEDEVICEMEM;
 
+/******************************************************************************
+ *     'bridge in' create Cmd Q
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_CREATECOMMANDQUEUE_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
 #else
@@ -488,9 +657,12 @@ typedef struct PVRSRV_BRIDGE_IN_CREATECOMMANDQUEUE_TAG
 }PVRSRV_BRIDGE_IN_CREATECOMMANDQUEUE;
 
 
+/******************************************************************************
+ *     'bridge in' destroy Cmd Q
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_DESTROYCOMMANDQUEUE_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
 #else
@@ -501,31 +673,40 @@ typedef struct PVRSRV_BRIDGE_IN_DESTROYCOMMANDQUEUE_TAG
 }PVRSRV_BRIDGE_IN_DESTROYCOMMANDQUEUE;
 
 
+/******************************************************************************
+ *     'bridge in' get full map data
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_MHANDLE_TO_MMAP_DATA_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
-       IMG_SID                         hMHandle;        
+       IMG_SID                         hMHandle;        /* Handle associated with the memory that needs to be mapped */
 #else
-       IMG_HANDLE                      hMHandle;        
+       IMG_HANDLE                      hMHandle;        /* Handle associated with the memory that needs to be mapped */
 #endif
 } PVRSRV_BRIDGE_IN_MHANDLE_TO_MMAP_DATA;
 
 
+/******************************************************************************
+ *     'bridge in' get full map data
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_RELEASE_MMAP_DATA_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
-       IMG_SID                         hMHandle;        
+       IMG_SID                         hMHandle;        /* Handle associated with the memory that needs to be mapped */
 #else
-       IMG_HANDLE                      hMHandle;        
+       IMG_HANDLE                      hMHandle;        /* Handle associated with the memory that needs to be mapped */
 #endif
 } PVRSRV_BRIDGE_IN_RELEASE_MMAP_DATA;
 
 
+/******************************************************************************
+ *     'bridge in' reserve vm
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_RESERVE_DEV_VIRTMEM_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevMemHeap;
 #else
@@ -537,6 +718,9 @@ typedef struct PVRSRV_BRIDGE_IN_RESERVE_DEV_VIRTMEM_TAG
 
 }PVRSRV_BRIDGE_IN_RESERVE_DEV_VIRTMEM;
 
+/******************************************************************************
+ *     'bridge out' connect to services
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_CONNECT_SERVICES_TAG
 {
        PVRSRV_ERROR    eError;
@@ -547,6 +731,9 @@ typedef struct PVRSRV_BRIDGE_OUT_CONNECT_SERVICES_TAG
 #endif
 }PVRSRV_BRIDGE_OUT_CONNECT_SERVICES;
 
+/******************************************************************************
+ *     'bridge out' reserve vm
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_RESERVE_DEV_VIRTMEM_TAG
 {
        PVRSRV_ERROR            eError;
@@ -563,9 +750,12 @@ typedef struct PVRSRV_BRIDGE_OUT_RESERVE_DEV_VIRTMEM_TAG
 }PVRSRV_BRIDGE_OUT_RESERVE_DEV_VIRTMEM;
 
 
+/******************************************************************************
+ *     'bridge in' free vm
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_FREE_DEV_VIRTMEM_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hKernelMemInfo;
 #else
@@ -577,9 +767,12 @@ typedef struct PVRSRV_BRIDGE_IN_FREE_DEV_VIRTMEM_TAG
 }PVRSRV_BRIDGE_IN_FREE_DEV_VIRTMEM;
 
 
+/******************************************************************************
+ *     'bridge in' map dev memory allocation to another heap
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_MAP_DEV_MEMORY_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hKernelMemInfo;
        IMG_SID                                 hDstDevMemHeap;
@@ -591,6 +784,9 @@ typedef struct PVRSRV_BRIDGE_IN_MAP_DEV_MEMORY_TAG
 }PVRSRV_BRIDGE_IN_MAP_DEV_MEMORY;
 
 
+/******************************************************************************
+ *     'bridge out' map dev memory allocation to another heap
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_MAP_DEV_MEMORY_TAG
 {
        PVRSRV_ERROR            eError;
@@ -605,9 +801,12 @@ typedef struct PVRSRV_BRIDGE_OUT_MAP_DEV_MEMORY_TAG
 }PVRSRV_BRIDGE_OUT_MAP_DEV_MEMORY;
 
 
+/******************************************************************************
+ *     'bridge in' unmap dev memory allocation
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_UNMAP_DEV_MEMORY_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hKernelMemInfo;
 #else
@@ -619,9 +818,12 @@ typedef struct PVRSRV_BRIDGE_IN_UNMAP_DEV_MEMORY_TAG
 }PVRSRV_BRIDGE_IN_UNMAP_DEV_MEMORY;
 
 
+/******************************************************************************
+ *     'bridge in' map pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_MAP_EXT_MEMORY_TAG
 {
-       IMG_UINT32       ui32BridgeFlags; 
+       IMG_UINT32       ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID          hKernelMemInfo;
 #else
@@ -632,18 +834,24 @@ typedef struct PVRSRV_BRIDGE_IN_MAP_EXT_MEMORY_TAG
 
 }PVRSRV_BRIDGE_IN_MAP_EXT_MEMORY;
 
+/******************************************************************************
+ *     'bridge in' unmap pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_UNMAP_EXT_MEMORY_TAG
 {
-       IMG_UINT32                                      ui32BridgeFlags; 
+       IMG_UINT32                                      ui32BridgeFlags; /* Must be first member of structure */
        PVRSRV_CLIENT_MEM_INFO          sClientMemInfo;
        PVRSRV_CLIENT_SYNC_INFO         sClientSyncInfo;
        IMG_UINT32                                      ui32Flags;
 
 }PVRSRV_BRIDGE_IN_UNMAP_EXT_MEMORY;
 
+/******************************************************************************
+ *     'bridge in' map device class buffer pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_MAP_DEVICECLASS_MEMORY_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDeviceClassBuffer;
        IMG_SID                 hDevMemContext;
@@ -655,6 +863,9 @@ typedef struct PVRSRV_BRIDGE_IN_MAP_DEVICECLASS_MEMORY_TAG
 }PVRSRV_BRIDGE_IN_MAP_DEVICECLASS_MEMORY;
 
 
+/******************************************************************************
+ *     'bridge out' map device class buffer pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_MAP_DEVICECLASS_MEMORY_TAG
 {
        PVRSRV_ERROR            eError;
@@ -671,9 +882,12 @@ typedef struct PVRSRV_BRIDGE_OUT_MAP_DEVICECLASS_MEMORY_TAG
 }PVRSRV_BRIDGE_OUT_MAP_DEVICECLASS_MEMORY;
 
 
+/******************************************************************************
+ *     'bridge in' unmap device class buffer pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_UNMAP_DEVICECLASS_MEMORY_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hKernelMemInfo;
 #else
@@ -685,9 +899,12 @@ typedef struct PVRSRV_BRIDGE_IN_UNMAP_DEVICECLASS_MEMORY_TAG
 }PVRSRV_BRIDGE_IN_UNMAP_DEVICECLASS_MEMORY;
 
 
+/******************************************************************************
+ *     'bridge in' pdump memory poll
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_MEMPOL_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelMemInfo;
 #else
@@ -701,9 +918,12 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_MEMPOL_TAG
 
 }PVRSRV_BRIDGE_IN_PDUMP_MEMPOL;
 
+/******************************************************************************
+ *     'bridge in' pdump sync poll
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_SYNCPOL_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfo;
 #else
@@ -717,9 +937,12 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_SYNCPOL_TAG
 }PVRSRV_BRIDGE_IN_PDUMP_SYNCPOL;
 
 
+/******************************************************************************
+ *     'bridge in' pdump dump memory
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPMEM_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_PVOID  pvLinAddr;
        IMG_PVOID  pvAltLinAddr;
 #if defined (SUPPORT_SID_INTERFACE)
@@ -734,9 +957,12 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPMEM_TAG
 }PVRSRV_BRIDGE_IN_PDUMP_DUMPMEM;
 
 
+/******************************************************************************
+ *     'bridge in' pdump dump sync
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPSYNC_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_PVOID  pvAltLinAddr;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfo;
@@ -749,9 +975,12 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPSYNC_TAG
 }PVRSRV_BRIDGE_IN_PDUMP_DUMPSYNC;
 
 
+/******************************************************************************
+ *     'bridge in' pdump dump reg
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPREG_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDevCookie;
 #else
@@ -763,9 +992,12 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPREG_TAG
 
 }PVRSRV_BRIDGE_IN_PDUMP_DUMPREG;
 
+/******************************************************************************
+ *     'bridge in' pdump dump reg
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_REGPOL_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -777,17 +1009,23 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_REGPOL_TAG
        IMG_CHAR   szRegRegion[32];
 }PVRSRV_BRIDGE_IN_PDUMP_REGPOL;
 
+/******************************************************************************
+ *     'bridge in' pdump dump PD reg
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPPDREG_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        PVRSRV_HWREG sHWReg;
        IMG_UINT32 ui32Flags;
 
 }PVRSRV_BRIDGE_IN_PDUMP_DUMPPDREG;
 
+/******************************************************************************
+ *     'bridge in' pdump dump mem pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_MEMPAGES_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
        IMG_SID                         hKernelMemInfo;
@@ -804,26 +1042,36 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_MEMPAGES_TAG
 
 }PVRSRV_BRIDGE_IN_PDUMP_MEMPAGES;
 
+/******************************************************************************
+ *     'bridge in' pdump dump comment
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_COMMENT_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_CHAR szComment[PVRSRV_PDUMP_MAX_COMMENT_SIZE];
        IMG_UINT32 ui32Flags;
 
 }PVRSRV_BRIDGE_IN_PDUMP_COMMENT;
 
 
+/******************************************************************************
+ *     'bridge in' pdump set frame
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_SETFRAME_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_UINT32 ui32Frame;
 
 }PVRSRV_BRIDGE_IN_PDUMP_SETFRAME;
 
 
+/******************************************************************************
+ *     'bridge in' pdump dump bitmap
+ *****************************************************************************/
+
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_BITMAP_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -848,9 +1096,12 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_BITMAP_TAG
 }PVRSRV_BRIDGE_IN_PDUMP_BITMAP;
 
 
+/******************************************************************************
+ *     'bridge in' pdump dump read reg
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_READREG_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -865,9 +1116,12 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_READREG_TAG
 
 }PVRSRV_BRIDGE_IN_PDUMP_READREG;
 
+/******************************************************************************
+ *     'bridge in' pdump dump driver-info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_DRIVERINFO_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_CHAR szString[PVRSRV_PDUMP_MAX_COMMENT_SIZE];
        IMG_BOOL bContinuous;
 
@@ -875,7 +1129,7 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_DRIVERINFO_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPPDDEVPADDR_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelMemInfo;
 #else
@@ -885,9 +1139,12 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_DUMPPDDEVPADDR_TAG
        IMG_DEV_PHYADDR sPDDevPAddr;
 }PVRSRV_BRIDGE_IN_PDUMP_DUMPPDDEVPADDR;
 
+/******************************************************************************
+ *     'bridge in' pdump cycle count register read
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_PDUM_IN_CYCLE_COUNT_REG_READ_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -897,6 +1154,13 @@ typedef struct PVRSRV_BRIDGE_PDUM_IN_CYCLE_COUNT_REG_READ_TAG
        IMG_BOOL bLastFrame;
 }PVRSRV_BRIDGE_IN_PDUMP_CYCLE_COUNT_REG_READ;
 
+/*****************************************************************************
+ * Output structures for BRIDGEs
+ ****************************************************************************/
+
+/******************************************************************************
+ *     'bridge out' enum. devices
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_ENUMDEVICE_TAG
 {
        PVRSRV_ERROR eError;
@@ -906,6 +1170,9 @@ typedef struct PVRSRV_BRIDGE_OUT_ENUMDEVICE_TAG
 }PVRSRV_BRIDGE_OUT_ENUMDEVICE;
 
 
+/******************************************************************************
+ *     'bridge out' acquire device info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_ACQUIRE_DEVICEINFO_TAG
 {
 
@@ -919,6 +1186,9 @@ typedef struct PVRSRV_BRIDGE_OUT_ACQUIRE_DEVICEINFO_TAG
 } PVRSRV_BRIDGE_OUT_ACQUIRE_DEVICEINFO;
 
 
+/******************************************************************************
+ *     'bridge out' enum. class devices
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_ENUMCLASS_TAG
 {
        PVRSRV_ERROR eError;
@@ -928,9 +1198,12 @@ typedef struct PVRSRV_BRIDGE_OUT_ENUMCLASS_TAG
 }PVRSRV_BRIDGE_OUT_ENUMCLASS;
 
 
+/******************************************************************************
+ *     'bridge in' open display class devices
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_OPEN_DISPCLASS_DEVICE_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
        IMG_UINT32              ui32DeviceID;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDevCookie;
@@ -940,6 +1213,9 @@ typedef struct PVRSRV_BRIDGE_IN_OPEN_DISPCLASS_DEVICE_TAG
 
 }PVRSRV_BRIDGE_IN_OPEN_DISPCLASS_DEVICE;
 
+/******************************************************************************
+ *     'bridge out' open display class devices
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_OPEN_DISPCLASS_DEVICE_TAG
 {
        PVRSRV_ERROR    eError;
@@ -952,9 +1228,12 @@ typedef struct PVRSRV_BRIDGE_OUT_OPEN_DISPCLASS_DEVICE_TAG
 }PVRSRV_BRIDGE_OUT_OPEN_DISPCLASS_DEVICE;
 
 
+/******************************************************************************
+ *     'bridge in' wrap pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_WRAP_EXT_MEMORY_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDevCookie;
        IMG_SID                                 hDevMemContext;
@@ -972,6 +1251,9 @@ typedef struct PVRSRV_BRIDGE_IN_WRAP_EXT_MEMORY_TAG
 
 }PVRSRV_BRIDGE_IN_WRAP_EXT_MEMORY;
 
+/******************************************************************************
+ *     'bridge out' wrap pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_WRAP_EXT_MEMORY_TAG
 {
        PVRSRV_ERROR    eError;
@@ -980,9 +1262,12 @@ typedef struct PVRSRV_BRIDGE_OUT_WRAP_EXT_MEMORY_TAG
 
 }PVRSRV_BRIDGE_OUT_WRAP_EXT_MEMORY;
 
+/******************************************************************************
+ *     'bridge in' unwrap pages
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_UNWRAP_EXT_MEMORY_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelMemInfo;
 #else
@@ -999,6 +1284,9 @@ typedef struct PVRSRV_BRIDGE_IN_UNWRAP_EXT_MEMORY_TAG
 #define PVRSRV_MAX_DC_SWAPCHAIN_BUFFERS                        4
 #define PVRSRV_MAX_DC_CLIP_RECTS                               32
 
+/******************************************************************************
+ *     'bridge out' enum display class formats
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_ENUM_DISPCLASS_FORMATS_TAG
 {
        PVRSRV_ERROR    eError;
@@ -1008,9 +1296,12 @@ typedef struct PVRSRV_BRIDGE_OUT_ENUM_DISPCLASS_FORMATS_TAG
 }PVRSRV_BRIDGE_OUT_ENUM_DISPCLASS_FORMATS;
 
 
+/******************************************************************************
+ *     'bridge in' enum display class dims
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_ENUM_DISPCLASS_DIMS_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDeviceKM;
 #else
@@ -1021,6 +1312,9 @@ typedef struct PVRSRV_BRIDGE_IN_ENUM_DISPCLASS_DIMS_TAG
 }PVRSRV_BRIDGE_IN_ENUM_DISPCLASS_DIMS;
 
 
+/******************************************************************************
+ *     'bridge out' enum display class dims
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_ENUM_DISPCLASS_DIMS_TAG
 {
        PVRSRV_ERROR    eError;
@@ -1030,6 +1324,9 @@ typedef struct PVRSRV_BRIDGE_OUT_ENUM_DISPCLASS_DIMS_TAG
 }PVRSRV_BRIDGE_OUT_ENUM_DISPCLASS_DIMS;
 
 
+/******************************************************************************
+ *     'bridge out' enum display class dims
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GET_DISPCLASS_INFO_TAG
 {
        PVRSRV_ERROR    eError;
@@ -1038,6 +1335,9 @@ typedef struct PVRSRV_BRIDGE_OUT_GET_DISPCLASS_INFO_TAG
 }PVRSRV_BRIDGE_OUT_GET_DISPCLASS_INFO;
 
 
+/******************************************************************************
+ *     'bridge out' get display class system buffer
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GET_DISPCLASS_SYSBUFFER_TAG
 {
        PVRSRV_ERROR    eError;
@@ -1050,9 +1350,12 @@ typedef struct PVRSRV_BRIDGE_OUT_GET_DISPCLASS_SYSBUFFER_TAG
 }PVRSRV_BRIDGE_OUT_GET_DISPCLASS_SYSBUFFER;
 
 
+/******************************************************************************
+ *     'bridge in' create swap chain
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_CREATE_DISPCLASS_SWAPCHAIN_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDeviceKM;
 #else
@@ -1068,6 +1371,9 @@ typedef struct PVRSRV_BRIDGE_IN_CREATE_DISPCLASS_SWAPCHAIN_TAG
 } PVRSRV_BRIDGE_IN_CREATE_DISPCLASS_SWAPCHAIN;
 
 
+/******************************************************************************
+ *     'bridge out' create swap chain
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_CREATE_DISPCLASS_SWAPCHAIN_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1081,9 +1387,12 @@ typedef struct PVRSRV_BRIDGE_OUT_CREATE_DISPCLASS_SWAPCHAIN_TAG
 } PVRSRV_BRIDGE_OUT_CREATE_DISPCLASS_SWAPCHAIN;
 
 
+/******************************************************************************
+ *     'bridge in' destroy swap chain
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_DESTROY_DISPCLASS_SWAPCHAIN_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDeviceKM;
        IMG_SID                         hSwapChain;
@@ -1095,9 +1404,12 @@ typedef struct PVRSRV_BRIDGE_IN_DESTROY_DISPCLASS_SWAPCHAIN_TAG
 } PVRSRV_BRIDGE_IN_DESTROY_DISPCLASS_SWAPCHAIN;
 
 
+/******************************************************************************
+ *     'bridge in' set DST/SRC rect
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_SET_DISPCLASS_RECT_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDeviceKM;
        IMG_SID                         hSwapChain;
@@ -1110,9 +1422,12 @@ typedef struct PVRSRV_BRIDGE_IN_SET_DISPCLASS_RECT_TAG
 } PVRSRV_BRIDGE_IN_SET_DISPCLASS_RECT;
 
 
+/******************************************************************************
+ *     'bridge in' set DST/SRC colourkey
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_SET_DISPCLASS_COLOURKEY_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDeviceKM;
        IMG_SID                         hSwapChain;
@@ -1125,9 +1440,12 @@ typedef struct PVRSRV_BRIDGE_IN_SET_DISPCLASS_COLOURKEY_TAG
 } PVRSRV_BRIDGE_IN_SET_DISPCLASS_COLOURKEY;
 
 
+/******************************************************************************
+ *     'bridge in' get buffers (from swapchain)
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GET_DISPCLASS_BUFFERS_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDeviceKM;
        IMG_SID                         hSwapChain;
@@ -1139,6 +1457,9 @@ typedef struct PVRSRV_BRIDGE_IN_GET_DISPCLASS_BUFFERS_TAG
 } PVRSRV_BRIDGE_IN_GET_DISPCLASS_BUFFERS;
 
 
+/******************************************************************************
+ *     'bridge out' get buffers (from swapchain)
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GET_DISPCLASS_BUFFERS_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1148,13 +1469,16 @@ typedef struct PVRSRV_BRIDGE_OUT_GET_DISPCLASS_BUFFERS_TAG
 #else
        IMG_HANDLE                      ahBuffer[PVRSRV_MAX_DC_SWAPCHAIN_BUFFERS];
 #endif
-
+       IMG_SYS_PHYADDR         asPhyAddr[PVRSRV_MAX_DC_SWAPCHAIN_BUFFERS];
 } PVRSRV_BRIDGE_OUT_GET_DISPCLASS_BUFFERS;
 
 
+/******************************************************************************
+ *     'bridge in' swap to buffer
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_BUFFER_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDeviceKM;
        IMG_SID                         hBuffer;
@@ -1173,10 +1497,36 @@ typedef struct PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_BUFFER_TAG
 
 } PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_BUFFER;
 
+/******************************************************************************
+ *     'bridge in' swap to buffer
+ *****************************************************************************/
+typedef struct PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_BUFFER2_TAG
+{
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
+#if defined (SUPPORT_SID_INTERFACE)
+       IMG_SID                         hDeviceKM;
+       IMG_SID                         hSwapChain;
+#else
+       IMG_HANDLE                      hDeviceKM;
+       IMG_HANDLE                      hSwapChain;
+#endif
+       IMG_UINT32                      ui32SwapInterval;
+
+       IMG_UINT32                      ui32NumMemInfos;
+       PVRSRV_KERNEL_MEM_INFO  **ppsKernelMemInfos;
+       PVRSRV_KERNEL_SYNC_INFO **ppsKernelSyncInfos;
+
+       IMG_UINT32                      ui32PrivDataLength;
+       IMG_PVOID                       pvPrivData;
 
+} PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_BUFFER2;
+
+/******************************************************************************
+ *     'bridge in' swap to system buffer (primary)
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_SYSTEM_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDeviceKM;
        IMG_SID                         hSwapChain;
@@ -1188,9 +1538,12 @@ typedef struct PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_SYSTEM_TAG
 } PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_SYSTEM;
 
 
+/******************************************************************************
+ *     'bridge in' open buffer class device
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_OPEN_BUFFERCLASS_DEVICE_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        IMG_UINT32                      ui32DeviceID;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
@@ -1201,6 +1554,9 @@ typedef struct PVRSRV_BRIDGE_IN_OPEN_BUFFERCLASS_DEVICE_TAG
 } PVRSRV_BRIDGE_IN_OPEN_BUFFERCLASS_DEVICE;
 
 
+/******************************************************************************
+ *     'bridge out' open buffer class device
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_OPEN_BUFFERCLASS_DEVICE_TAG
 {
        PVRSRV_ERROR eError;
@@ -1213,6 +1569,9 @@ typedef struct PVRSRV_BRIDGE_OUT_OPEN_BUFFERCLASS_DEVICE_TAG
 } PVRSRV_BRIDGE_OUT_OPEN_BUFFERCLASS_DEVICE;
 
 
+/******************************************************************************
+ *     'bridge out' get buffer class info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GET_BUFFERCLASS_INFO_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1221,9 +1580,12 @@ typedef struct PVRSRV_BRIDGE_OUT_GET_BUFFERCLASS_INFO_TAG
 } PVRSRV_BRIDGE_OUT_GET_BUFFERCLASS_INFO;
 
 
+/******************************************************************************
+ *     'bridge in' get buffer class buffer
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GET_BUFFERCLASS_BUFFER_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDeviceKM;
 #else
@@ -1234,6 +1596,9 @@ typedef struct PVRSRV_BRIDGE_IN_GET_BUFFERCLASS_BUFFER_TAG
 } PVRSRV_BRIDGE_IN_GET_BUFFERCLASS_BUFFER;
 
 
+/******************************************************************************
+ *     'bridge out' get buffer class buffer
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GET_BUFFERCLASS_BUFFER_TAG
 {
        PVRSRV_ERROR eError;
@@ -1246,6 +1611,9 @@ typedef struct PVRSRV_BRIDGE_OUT_GET_BUFFERCLASS_BUFFER_TAG
 } PVRSRV_BRIDGE_OUT_GET_BUFFERCLASS_BUFFER;
 
 
+/******************************************************************************
+ *     'bridge out' get heap info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GET_DEVMEM_HEAPINFO_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1255,6 +1623,9 @@ typedef struct PVRSRV_BRIDGE_OUT_GET_DEVMEM_HEAPINFO_TAG
 } PVRSRV_BRIDGE_OUT_GET_DEVMEM_HEAPINFO;
 
 
+/******************************************************************************
+ *     'bridge out' create device memory context
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_CREATE_DEVMEMCONTEXT_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1269,6 +1640,9 @@ typedef struct PVRSRV_BRIDGE_OUT_CREATE_DEVMEMCONTEXT_TAG
 } PVRSRV_BRIDGE_OUT_CREATE_DEVMEMCONTEXT;
 
 
+/******************************************************************************
+ *     'bridge out' create device memory context
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_CREATE_DEVMEMHEAP_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1281,6 +1655,9 @@ typedef struct PVRSRV_BRIDGE_OUT_CREATE_DEVMEMHEAP_TAG
 } PVRSRV_BRIDGE_OUT_CREATE_DEVMEMHEAP;
 
 
+/******************************************************************************
+ *     'bridge out' alloc device memory
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_ALLOCDEVICEMEM_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1295,6 +1672,9 @@ typedef struct PVRSRV_BRIDGE_OUT_ALLOCDEVICEMEM_TAG
 } PVRSRV_BRIDGE_OUT_ALLOCDEVICEMEM;
 
 
+/******************************************************************************
+ *     'bridge out' export device memory
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_EXPORTDEVICEMEM_TAG
 {
        PVRSRV_ERROR                    eError;
@@ -1310,6 +1690,26 @@ typedef struct PVRSRV_BRIDGE_OUT_EXPORTDEVICEMEM_TAG
 } PVRSRV_BRIDGE_OUT_EXPORTDEVICEMEM;
 
 
+/******************************************************************************
+ *     'bridge out' map ion handle
+ *****************************************************************************/
+typedef struct _PVRSRV_BRIDGE_OUT_MAP_ION_HANDLE_
+{
+       PVRSRV_ERROR            eError;
+#if defined (SUPPORT_SID_INTERFACE)
+       IMG_SID                 hKernelMemInfo;
+#else
+       PVRSRV_KERNEL_MEM_INFO  *psKernelMemInfo;
+#endif
+       PVRSRV_CLIENT_MEM_INFO  sClientMemInfo;
+       PVRSRV_CLIENT_SYNC_INFO sClientSyncInfo;
+
+} PVRSRV_BRIDGE_OUT_MAP_ION_HANDLE;
+
+
+/******************************************************************************
+ *     'bridge out' map meminfo to user mode
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_MAPMEMINFOTOUSER_TAG
 {
        PVRSRV_ERROR                    eError;
@@ -1323,6 +1723,9 @@ typedef struct PVRSRV_BRIDGE_OUT_MAPMEMINFOTOUSER_TAG
 }PVRSRV_BRIDGE_OUT_MAPMEMINFOTOUSER;
 
 
+/******************************************************************************
+ *     'bridge out' get free device memory
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GETFREEDEVICEMEM_TAG
 {
        PVRSRV_ERROR eError;
@@ -1333,21 +1736,29 @@ typedef struct PVRSRV_BRIDGE_OUT_GETFREEDEVICEMEM_TAG
 } PVRSRV_BRIDGE_OUT_GETFREEDEVICEMEM;
 
 
+//#ifdef LINUX
+/******************************************************************************
+ *     'bridge out' get full map data
+ *****************************************************************************/
 #include "pvrmmap.h"
 typedef struct PVRSRV_BRIDGE_OUT_MHANDLE_TO_MMAP_DATA_TAG
 {
     PVRSRV_ERROR               eError;
 
-    
+    /* This is a the offset you should pass to mmap(2) so that
+     * the driver can look up the full details for the mapping
+     * request. */
      IMG_UINT32                        ui32MMapOffset;
 
-    
+    /* This is the byte offset you should add to the mapping you
+     * get from mmap */
     IMG_UINT32                 ui32ByteOffset;
 
-    
+    /* This is the real size of the mapping that will be created
+     * which should be passed to mmap _and_ munmap. */
     IMG_UINT32                         ui32RealByteSize;
 
-    
+    /* User mode address associated with mapping */
     IMG_UINT32                 ui32UserVAddr;
 
 } PVRSRV_BRIDGE_OUT_MHANDLE_TO_MMAP_DATA;
@@ -1356,23 +1767,32 @@ typedef struct PVRSRV_BRIDGE_OUT_RELEASE_MMAP_DATA_TAG
 {
     PVRSRV_ERROR               eError;
 
-    
+    /* Flag that indicates whether the mapping should be destroyed */
     IMG_BOOL                   bMUnmap;
 
-    
+    /* User mode address associated with mapping */
     IMG_UINT32                 ui32UserVAddr;
 
-    
+    /* Size of mapping */
     IMG_UINT32                 ui32RealByteSize;
 } PVRSRV_BRIDGE_OUT_RELEASE_MMAP_DATA;
+//#endif
+
+
+/******************************************************************************
+ *     'bridge in' get misc info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GET_MISC_INFO_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        PVRSRV_MISC_INFO        sMiscInfo;
 
 }PVRSRV_BRIDGE_IN_GET_MISC_INFO;
 
 
+/******************************************************************************
+ *     'bridge out' get misc info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GET_MISC_INFO_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1381,14 +1801,20 @@ typedef struct PVRSRV_BRIDGE_OUT_GET_MISC_INFO_TAG
 }PVRSRV_BRIDGE_OUT_GET_MISC_INFO;
 
 
+/******************************************************************************
+ *     'bridge in' get misc info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_RELEASE_MISC_INFO_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        PVRSRV_MISC_INFO        sMiscInfo;
 
 }PVRSRV_BRIDGE_IN_RELEASE_MISC_INFO;
 
 
+/******************************************************************************
+ *     'bridge out' get misc info
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_RELEASE_MISC_INFO_TAG
 {
        PVRSRV_ERROR            eError;
@@ -1397,6 +1823,10 @@ typedef struct PVRSRV_BRIDGE_OUT_RELEASE_MISC_INFO_TAG
 }PVRSRV_BRIDGE_OUT_RELEASE_MISC_INFO;
 
 
+/******************************************************************************
+ *     'bridge out' PDUMP is capturing
+ *****************************************************************************/
+
 typedef struct PVRSRV_BRIDGE_OUT_PDUMP_ISCAPTURING_TAG
 {
        PVRSRV_ERROR eError;
@@ -1404,18 +1834,24 @@ typedef struct PVRSRV_BRIDGE_OUT_PDUMP_ISCAPTURING_TAG
 
 } PVRSRV_BRIDGE_OUT_PDUMP_ISCAPTURING;
 
+/******************************************************************************
+ *     'bridge in' get FB mem stats
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_GET_FB_STATS_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_SIZE_T ui32Total;
        IMG_SIZE_T ui32Available;
 
 } PVRSRV_BRIDGE_IN_GET_FB_STATS;
 
 
+/******************************************************************************
+ *     'bridge in' Map CPU Physical to User Space
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_MAPPHYSTOUSERSPACE_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
 #else
@@ -1427,6 +1863,9 @@ typedef struct PVRSRV_BRIDGE_IN_MAPPHYSTOUSERSPACE_TAG
 } PVRSRV_BRIDGE_IN_MAPPHYSTOUSERSPACE;
 
 
+/******************************************************************************
+ *     'bridge out' Map CPU Physical to User Space
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_MAPPHYSTOUSERSPACE_TAG
 {
        IMG_PVOID                       pvUserAddr;
@@ -1436,9 +1875,12 @@ typedef struct PVRSRV_BRIDGE_OUT_MAPPHYSTOUSERSPACE_TAG
 } PVRSRV_BRIDGE_OUT_MAPPHYSTOUSERSPACE;
 
 
+/******************************************************************************
+ *     'bridge in' Unmap CPU Physical to User Space
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_UNMAPPHYSTOUSERSPACE_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
 #else
@@ -1450,6 +1892,9 @@ typedef struct PVRSRV_BRIDGE_IN_UNMAPPHYSTOUSERSPACE_TAG
 } PVRSRV_BRIDGE_IN_UNMAPPHYSTOUSERSPACE;
 
 
+/******************************************************************************
+ *     'bridge out' Get user space pointer to Phys to Lin lookup table
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_GETPHYSTOUSERSPACEMAP_TAG
 {
        IMG_PVOID                       *ppvTbl;
@@ -1459,19 +1904,25 @@ typedef struct PVRSRV_BRIDGE_OUT_GETPHYSTOUSERSPACEMAP_TAG
 
 
 #if !defined (SUPPORT_SID_INTERFACE)
+/******************************************************************************
+ *     'bridge in' Register RTSIM process thread
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_REGISTER_SIM_PROCESS_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        IMG_HANDLE                      hDevCookie;
        IMG_PVOID                       pvProcess;
 
 } PVRSRV_BRIDGE_IN_REGISTER_SIM_PROCESS;
 
 
+/******************************************************************************
+ *     'bridge out' Register RTSIM process thread
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_REGISTER_SIM_PROCESS_TAG
 {
-       IMG_SYS_PHYADDR         sRegsPhysBase;                  
-       IMG_VOID                        *pvRegsBase;                    
+       IMG_SYS_PHYADDR         sRegsPhysBase;                  /*!< Physical address of current device register */
+       IMG_VOID                        *pvRegsBase;                    /*!< User mode linear address of SGX device registers */
        IMG_PVOID                       pvProcess;
        IMG_UINT32                      ulNoOfEntries;
        IMG_PVOID                       pvTblLinAddr;
@@ -1479,35 +1930,44 @@ typedef struct PVRSRV_BRIDGE_OUT_REGISTER_SIM_PROCESS_TAG
 } PVRSRV_BRIDGE_OUT_REGISTER_SIM_PROCESS;
 
 
+/******************************************************************************
+ *     'bridge in' Unregister RTSIM process thread
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_UNREGISTER_SIM_PROCESS_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        IMG_HANDLE                      hDevCookie;
        IMG_PVOID                       pvProcess;
-       IMG_VOID                        *pvRegsBase;                    
+       IMG_VOID                        *pvRegsBase;                    /*!< User mode linear address of SGX device registers */
 
 } PVRSRV_BRIDGE_IN_UNREGISTER_SIM_PROCESS;
 
+/******************************************************************************
+ *     'bridge in' process simulator ISR event
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_PROCESS_SIMISR_EVENT_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        IMG_HANDLE                      hDevCookie;
        IMG_UINT32                      ui32StatusAndMask;
        PVRSRV_ERROR            eError;
 
 } PVRSRV_BRIDGE_IN_PROCESS_SIMISR_EVENT;
-#endif 
+#endif /* #if !defined (SUPPORT_SID_INTERFACE) */
 
+/******************************************************************************
+ *     'bridge in' initialisation server disconnect
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_INITSRV_DISCONNECT_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
        IMG_BOOL                        bInitSuccesful;
 } PVRSRV_BRIDGE_IN_INITSRV_DISCONNECT;
 
 
 typedef struct PVRSRV_BRIDGE_IN_ALLOC_SHARED_SYS_MEM_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
     IMG_UINT32 ui32Flags;
     IMG_SIZE_T ui32Size;
 }PVRSRV_BRIDGE_IN_ALLOC_SHARED_SYS_MEM;
@@ -1528,7 +1988,7 @@ typedef struct PVRSRV_BRIDGE_IN_FREE_SHARED_SYS_MEM_TAG
        IMG_SID                 hKernelMemInfo;
        IMG_SID                 hMappingInfo;
 #else
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
        PVRSRV_KERNEL_MEM_INFO  *psKernelMemInfo;
 #endif
        PVRSRV_CLIENT_MEM_INFO  sClientMemInfo;
@@ -1541,7 +2001,7 @@ typedef struct PVRSRV_BRIDGE_OUT_FREE_SHARED_SYS_MEM_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_MAP_MEMINFO_MEM_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelMemInfo;
 #else
@@ -1563,7 +2023,7 @@ typedef struct PVRSRV_BRIDGE_OUT_MAP_MEMINFO_MEM_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_UNMAP_MEMINFO_MEM_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        PVRSRV_CLIENT_MEM_INFO sClientMemInfo;
 }PVRSRV_BRIDGE_IN_UNMAP_MEMINFO_MEM;
 
@@ -1574,7 +2034,7 @@ typedef struct PVRSRV_BRIDGE_OUT_UNMAP_MEMINFO_MEM_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_EVENT_OBJECT_WAI_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID         hOSEventKM;
 #else
@@ -1621,7 +2081,7 @@ typedef struct PVRSRV_BRIDGE_OUT_CREATE_SYNC_INFO_MOD_OBJ_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_DESTROY_SYNC_INFO_MOD_OBJ
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfoModObj;
 #else
@@ -1631,7 +2091,7 @@ typedef struct PVRSRV_BRIDGE_IN_DESTROY_SYNC_INFO_MOD_OBJ
 
 typedef struct PVRSRV_BRIDGE_IN_MODIFY_PENDING_SYNC_OPS_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfoModObj;
        IMG_SID    hKernelSyncInfo;
@@ -1645,7 +2105,7 @@ typedef struct PVRSRV_BRIDGE_IN_MODIFY_PENDING_SYNC_OPS_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_MODIFY_COMPLETE_SYNC_OPS_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfoModObj;
 #else
@@ -1657,15 +2117,16 @@ typedef struct PVRSRV_BRIDGE_OUT_MODIFY_PENDING_SYNC_OPS_TAG
 {
        PVRSRV_ERROR eError;
 
-       
+       /* The following variable are used to return the PRE-INCREMENTED op vals */
        IMG_UINT32 ui32ReadOpsPending;
        IMG_UINT32 ui32WriteOpsPending;
+       IMG_UINT32 ui32ReadOps2Pending;
 
 } PVRSRV_BRIDGE_OUT_MODIFY_PENDING_SYNC_OPS;
 
 typedef struct PVRSRV_BRIDGE_IN_SYNC_OPS_TAKE_TOKEN_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfo;
 #else
@@ -1680,12 +2141,13 @@ typedef struct PVRSRV_BRIDGE_OUT_SYNC_OPS_TAKE_TOKEN_TAG
 
        IMG_UINT32 ui32ReadOpsPending;
        IMG_UINT32 ui32WriteOpsPending;
+       IMG_UINT32 ui32ReadOps2Pending;
 
 } PVRSRV_BRIDGE_OUT_SYNC_OPS_TAKE_TOKEN;
 
 typedef struct PVRSRV_BRIDGE_IN_SYNC_OPS_FLUSH_TO_TOKEN_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfo;
 #else
@@ -1693,11 +2155,12 @@ typedef struct PVRSRV_BRIDGE_IN_SYNC_OPS_FLUSH_TO_TOKEN_TAG
 #endif
        IMG_UINT32 ui32ReadOpsPendingSnapshot;
        IMG_UINT32 ui32WriteOpsPendingSnapshot;
+       IMG_UINT32 ui32ReadOps2PendingSnapshot;
 } PVRSRV_BRIDGE_IN_SYNC_OPS_FLUSH_TO_TOKEN;
 
 typedef struct PVRSRV_BRIDGE_IN_SYNC_OPS_FLUSH_TO_MOD_OBJ_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfoModObj;
 #else
@@ -1707,7 +2170,7 @@ typedef struct PVRSRV_BRIDGE_IN_SYNC_OPS_FLUSH_TO_MOD_OBJ_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SYNC_OPS_FLUSH_TO_DELTA_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfo;
 #else
@@ -1718,7 +2181,7 @@ typedef struct PVRSRV_BRIDGE_IN_SYNC_OPS_FLUSH_TO_DELTA_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_ALLOC_SYNC_INFO_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
@@ -1740,7 +2203,7 @@ typedef struct PVRSRV_BRIDGE_OUT_ALLOC_SYNC_INFO_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_FREE_SYNC_INFO_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hKernelSyncInfo;
@@ -1760,5 +2223,9 @@ typedef struct PVRSRV_BRIDGE_IN_CHG_DEV_MEM_ATTRIBS_TAG
 }
 #endif
 
-#endif 
+#endif /* __PVR_BRIDGE_H__ */
+
+/******************************************************************************
+ End of file (pvr_bridge.h)
+******************************************************************************/
 
index 1175b76..3a1cac8 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PVR Bridge Functionality
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Header for the PVR Bridge code
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __PVR_BRIDGE_KM_H_
 #define __PVR_BRIDGE_KM_H_
@@ -34,6 +50,9 @@ extern "C" {
 #include "pvr_bridge.h"
 #include "perproc.h"
 
+/******************************************************************************
+ * Function prototypes
+ *****************************************************************************/
 #if defined(__linux__)
 PVRSRV_ERROR LinuxBridgeInit(IMG_VOID);
 IMG_VOID LinuxBridgeDeInit(IMG_VOID);
@@ -103,17 +122,27 @@ PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                                      hDevCookie,
                                                                                                 IMG_UINT32                                     ui32Flags,
                                                                                                 IMG_SIZE_T                                     ui32Size,
                                                                                                 IMG_SIZE_T                                     ui32Alignment,
+                                                                                                IMG_PVOID                                      pvPrivData,
+                                                                                                IMG_UINT32                                     ui32PrivDataLength,
+                                                                                                IMG_UINT32                                     ui32ChunkSize,
+                                                                                                IMG_UINT32                                     ui32NumVirtChunks,
+                                                                                                IMG_UINT32                                     ui32NumPhysChunks,
+                                                                                                IMG_BOOL                                       *pabMapChunk,
                                                                                                 PVRSRV_KERNEL_MEM_INFO         **ppsMemInfo);
 
 
 #if defined(PVRSRV_LOG_MEMORY_ALLOCS)
-       #define PVRSRVAllocDeviceMemKM(devCookie, perProc, devMemHeap, flags, size, alignment, memInfo, logStr) \
+       #define PVRSRVAllocDeviceMemKM(devCookie, perProc, devMemHeap, flags, size, alignment, privdata, privdatalength, \
+                                                                  chunksize, numvirtchunks, numphyschunks, mapchunk, memInfo, logStr) \
                (PVR_TRACE(("PVRSRVAllocDeviceMemKM(" #devCookie ", " #perProc ", " #devMemHeap ", " #flags ", " #size \
                        ", " #alignment "," #memInfo "): " logStr " (size = 0x%x)", size)),\
-                       _PVRSRVAllocDeviceMemKM(devCookie, perProc, devMemHeap, flags, size, alignment, memInfo))
+                       _PVRSRVAllocDeviceMemKM(devCookie, perProc, devMemHeap, flags, size, alignment, privdata, privdatalength, \
+                                                                       chunksize, numvirtchunks, numphyschunks, mapchunk, memInfo))
 #else
-       #define PVRSRVAllocDeviceMemKM(devCookie, perProc, devMemHeap, flags, size, alignment, memInfo, logStr) \
-                       _PVRSRVAllocDeviceMemKM(devCookie, perProc, devMemHeap, flags, size, alignment, memInfo)
+       #define PVRSRVAllocDeviceMemKM(devCookie, perProc, devMemHeap, flags, size, alignment, privdata, privdatalength, \
+                                                                  chunksize, numvirtchunks, numphyschunks, mapchunk, memInfo, logStr) \
+                       _PVRSRVAllocDeviceMemKM(devCookie, perProc, devMemHeap, flags, size, alignment, privdata, privdatalength, \
+                                                                       chunksize, numvirtchunks, numphyschunks, mapchunk, memInfo)
 #endif
 
 
@@ -121,6 +150,20 @@ IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVFreeDeviceMemKM(IMG_HANDLE                     hDevCookie,
                                                                                                PVRSRV_KERNEL_MEM_INFO  *psMemInfo);
 
+#if defined(SUPPORT_ION)
+IMG_IMPORT
+PVRSRV_ERROR PVRSRVMapIonHandleKM(PVRSRV_PER_PROCESS_DATA *psPerProc,
+                                                                 IMG_HANDLE hDevCookie,
+                                                                 IMG_HANDLE hDevMemContext,
+                                                                 IMG_HANDLE hIon,
+                                                                 IMG_UINT32 ui32Flags,
+                                                                 IMG_UINT32 ui32Size,
+                                                                 PVRSRV_KERNEL_MEM_INFO **ppsKernelMemInfo);
+
+IMG_IMPORT
+PVRSRV_ERROR IMG_CALLCONV PVRSRVUnmapIonHandleKM(PVRSRV_KERNEL_MEM_INFO *psMemInfo);
+#endif /* SUPPORT_ION */
+
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVDissociateDeviceMemKM(IMG_HANDLE                       hDevCookie,
                                                                                                PVRSRV_KERNEL_MEM_INFO  *psMemInfo);
@@ -171,7 +214,7 @@ PVRSRV_ERROR PVRSRVOpenDCDeviceKM(PVRSRV_PER_PROCESS_DATA   *psPerProc,
                                                                  IMG_HANDLE                            *phDeviceKM);
 
 IMG_IMPORT
-PVRSRV_ERROR PVRSRVCloseDCDeviceKM(IMG_HANDLE hDeviceKM, IMG_BOOL bResManCallback);
+PVRSRV_ERROR PVRSRVCloseDCDeviceKM(IMG_HANDLE hDeviceKM);
 
 IMG_IMPORT
 PVRSRV_ERROR PVRSRVEnumDCFormatsKM(IMG_HANDLE hDeviceKM,
@@ -223,7 +266,8 @@ IMG_IMPORT
 PVRSRV_ERROR PVRSRVGetDCBuffersKM(IMG_HANDLE   hDeviceKM,
                                                                  IMG_HANDLE    hSwapChain,
                                                                  IMG_UINT32    *pui32BufferCount,
-                                                                 IMG_HANDLE    *phBuffer);
+                                                                 IMG_HANDLE    *phBuffer,
+                                                                 IMG_SYS_PHYADDR *psPhyAddr);
 IMG_IMPORT
 PVRSRV_ERROR PVRSRVSwapToDCBufferKM(IMG_HANDLE hDeviceKM,
                                                                        IMG_HANDLE      hBuffer,
@@ -232,6 +276,15 @@ PVRSRV_ERROR PVRSRVSwapToDCBufferKM(IMG_HANDLE     hDeviceKM,
                                                                        IMG_UINT32      ui32ClipRectCount,
                                                                        IMG_RECT        *psClipRect);
 IMG_IMPORT
+PVRSRV_ERROR PVRSRVSwapToDCBuffer2KM(IMG_HANDLE        hDeviceKM,
+                                                                        IMG_HANDLE     hBuffer,
+                                                                        IMG_UINT32     ui32SwapInterval,
+                                                                        PVRSRV_KERNEL_MEM_INFO **ppsMemInfos,
+                                                                        PVRSRV_KERNEL_SYNC_INFO **ppsSyncInfos,
+                                                                        IMG_UINT32     ui32NumMemSyncInfos,
+                                                                        IMG_PVOID      pvPrivData,
+                                                                        IMG_UINT32     ui32PrivDataLength);
+IMG_IMPORT
 PVRSRV_ERROR PVRSRVSwapToDCSystemKM(IMG_HANDLE hDeviceKM,
                                                                        IMG_HANDLE      hSwapChain);
 
@@ -241,7 +294,7 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM(PVRSRV_PER_PROCESS_DATA   *psPerProc,
                                                                  IMG_HANDLE                            hDevCookie,
                                                                  IMG_HANDLE                            *phDeviceKM);
 IMG_IMPORT
-PVRSRV_ERROR PVRSRVCloseBCDeviceKM(IMG_HANDLE hDeviceKM, IMG_BOOL bResManCallback);
+PVRSRV_ERROR PVRSRVCloseBCDeviceKM(IMG_HANDLE hDeviceKM);
 
 IMG_IMPORT
 PVRSRV_ERROR PVRSRVGetBCInfoKM(IMG_HANDLE      hDeviceKM,
@@ -276,7 +329,9 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocSyncInfoKM(IMG_HANDLE                                  hDevCookie,
                                                                                                IMG_HANDLE                                      hDevMemContext,
                                                                                                PVRSRV_KERNEL_SYNC_INFO **ppsKernelSyncInfo);
 IMG_IMPORT
-PVRSRV_ERROR IMG_CALLCONV PVRSRVFreeSyncInfoKM(PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo);
+IMG_VOID IMG_CALLCONV PVRSRVAcquireSyncInfoKM(PVRSRV_KERNEL_SYNC_INFO  *psKernelSyncInfo);
+IMG_IMPORT
+IMG_VOID IMG_CALLCONV PVRSRVReleaseSyncInfoKM(PVRSRV_KERNEL_SYNC_INFO  *psKernelSyncInfo);
 
 IMG_IMPORT
 #if defined (SUPPORT_SID_INTERFACE)
@@ -285,15 +340,52 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO_KM *psMiscInfo);
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo);
 #endif
 
+/*!
+ * *****************************************************************************
+ * @brief Allocates memory on behalf of a userspace process that is addressable
+ *        by ther kernel. The memory is suitable for mapping into
+ *        user space and it is possible to entirely dissociate the memory
+ *        from the userspace process via PVRSRVDissociateSharedSysMemoryKM.
+ *
+ * @param psPerProc
+ * @param ui32Flags
+ * @param ui32Size
+ * @param ppsKernelMemInfo
+ *
+ * @return PVRSRV_ERROR
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR
 PVRSRVAllocSharedSysMemoryKM(PVRSRV_PER_PROCESS_DATA   *psPerProc,
                                                         IMG_UINT32                             ui32Flags,
                                                         IMG_SIZE_T                             ui32Size,
                                                         PVRSRV_KERNEL_MEM_INFO         **ppsKernelMemInfo);
 
+/*!
+ * *****************************************************************************
+ * @brief Frees memory allocated via PVRSRVAllocSharedSysMemoryKM (Note you must
+ *        be sure any additional kernel references you created have been
+ *        removed before freeing the memory)
+ *
+ * @param psKernelMemInfo
+ *
+ * @return PVRSRV_ERROR
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR
 PVRSRVFreeSharedSysMemoryKM(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo);
 
+/*!
+******************************************************************************
+
+ @brief        Dissociates memory from the process that allocates it.  Intended for
+ transfering the ownership of system memory from a particular process
+ to the kernel.  Unlike PVRSRVDissociateDeviceMemKM, ownership is not
+ transfered to the kernel context, so the Resource Manager will not
+ automatically clean up such memory.
+
+ @param           psKernelMemInfo:
+
+ @return   PVRSRV_ERROR:
+******************************************************************************/
 IMG_IMPORT PVRSRV_ERROR
 PVRSRVDissociateMemFromResmanKM(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo);
 
@@ -301,5 +393,8 @@ PVRSRVDissociateMemFromResmanKM(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo);
 }
 #endif
 
-#endif 
+#endif /* __PVR_BRIDGE_KM_H_ */
 
+/******************************************************************************
+ End of file (pvr_bridge_km.h)
+******************************************************************************/
index 242d953..1a3930c 100644 (file)
@@ -1,32 +1,59 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Main include file for PVRMMAP library.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __PVRMMAP_H__
 #define __PVRMMAP_H__
 
+/*!
+ **************************************************************************
+ @brief         map kernel memory into user memory. 
+
+ @param                        hModule - a handle to the device supplying the kernel memory
+ @param                        ppvLinAddr - pointer to where the user mode address should be placed
+ @param                        pvLinAddrKM - the base of kernel address range to map
+ @param                        phMappingInfo - pointer to mapping information handle
+ @param                        hMHandle - handle associated with memory to be mapped
+
+ @return               PVRSRV_OK, or error code.
+ ***************************************************************************/
+
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRPMapKMem(IMG_HANDLE hModule, IMG_VOID **ppvLinAddr, IMG_VOID *pvLinAddrKM, IMG_SID *phMappingInfo, IMG_SID hMHandle);
 #else
@@ -34,11 +61,21 @@ PVRSRV_ERROR PVRPMapKMem(IMG_HANDLE hModule, IMG_VOID **ppvLinAddr, IMG_VOID *pv
 #endif
 
 
+/*!
+ **************************************************************************
+ @brief                Removes a kernel to userspace memory mapping.
+
+ @param                hModule - a handle to the device supplying the kernel memory
+ @param                hMappingInfo - mapping information handle
+ @param                hMHandle - handle associated with memory to be mapped
+
+ @return       IMG_BOOL indicating success or otherwise.
+ ***************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 IMG_BOOL PVRUnMapKMem(IMG_HANDLE hModule, IMG_SID hMappingInfo, IMG_SID hMHandle);
 #else
 IMG_BOOL PVRUnMapKMem(IMG_HANDLE hModule, IMG_HANDLE hMappingInfo, IMG_HANDLE hMHandle);
 #endif
 
-#endif 
+#endif /* _PVRMMAP_H_ */
 
index 5474984..2e95810 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          error code to string translation utility
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    error code to string translation utility
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined (__PVRSRV_ERRORS_H__)
 #define __PVRSRV_ERRORS_H__
 extern "C" {
 #endif
 
+/*
+       NOTE: TO BE INCLUDED ONLY ONCE IN THE UM AND KM SERVICES MODULES
+       PROVIDES IMPLEMENTATIONS OF
+
+       MUST BE KEPT IN SYNC WITH SERVICESEXT.H
+
+       PVRSRVGetErrorString
+       PVRSRVGetErrorStringKM
+       Specifically, we have
+
+       resources.c:
+       IMG_EXPORT
+       const IMG_CHAR *PVRSRVGetErrorString(PVRSRV_ERROR eError)
+       {
+       #include "pvrsrv_errors.h"
+       }
+
+       pvrsrv.c:
+       IMG_EXPORT
+       const IMG_CHAR *PVRSRVGetErrorStringKM(PVRSRV_ERROR eError)
+       {
+       #include "pvrsrv_errors.h"
+       }
+*/
        switch (eError)
        {
                case PVRSRV_OK:                                                                 return "No Errors";
@@ -253,6 +293,8 @@ extern "C" {
                case PVRSRV_ERROR_UNKNOWN_SGL_ERROR:                    return "PVRSRV_ERROR_UNKNOWN_SGL_ERROR";
            case PVRSRV_ERROR_BAD_SYNC_STATE:               return "PVRSRV_ERROR_BAD_SYNC_STATE";
 
+           case PVRSRV_ERROR_CACHE_INVALIDATE_FAILED:      return "PVRSRV_ERROR_CACHE_INVALIDATE_FAILED";
+
                case PVRSRV_ERROR_FORCE_I32:                                    return "PVRSRV_ERROR_FORCE_I32";
 
                default:
@@ -262,5 +304,8 @@ extern "C" {
 #if defined (__cplusplus)
 }
 #endif
-#endif 
+#endif /* __PVRSRV_ERRORS_H__ */
 
+/*****************************************************************************
+ End of file (pvrsrv_errors.h)
+*****************************************************************************/
index efd8f50..32e19f9 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Services Internal Header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    services internal details
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined (__SERVICESINT_H__)
 #define __SERVICESINT_H__
@@ -33,11 +49,15 @@ extern "C" {
 
 #include "services.h"
 #include "sysinfo.h"
+#include "sysconfig.h"
 
 #define HWREC_DEFAULT_TIMEOUT  (500)
 
 #define DRIVERNAME_MAXLENGTH   (100)
 
+/*
+       helper macros:
+*/
 #define        ALIGNSIZE(size, alignshift)     (((size) + ((1UL << (alignshift))-1)) & ~((1UL << (alignshift))-1))
 
 #ifndef MAX
@@ -47,6 +67,18 @@ extern "C" {
 #define MIN(a,b)                                       (((a) < (b)) ? (a) : (b))
 #endif
 
+/*
+       Note:
+       MAX_CLEANUP_TRYS is set to try and be around the frame rate
+       as for every try we will kick the uKernel which we want to avoid
+       doing too often (as we risk flooding the uKernel trace buffer
+       with requests and losing important information from before the
+       cleanup requests started).
+*/
+#define MAX_CLEANUP_TIME_US                    (MAX_HW_TIME_US * 4)
+#define MAX_CLEANUP_TRYS                       100
+#define MAX_CLEANUP_TIME_WAIT_US       (MAX_CLEANUP_TIME_US/MAX_CLEANUP_TRYS)
+
 typedef enum _PVRSRV_MEMTYPE_
 {
        PVRSRV_MEMTYPE_UNKNOWN          = 0,
@@ -54,70 +86,79 @@ typedef enum _PVRSRV_MEMTYPE_
        PVRSRV_MEMTYPE_DEVICECLASS      = 2,
        PVRSRV_MEMTYPE_WRAPPED          = 3,
        PVRSRV_MEMTYPE_MAPPED           = 4,
+       PVRSRV_MEMTYPE_ION                      = 5,
 } PVRSRV_MEMTYPE;
 
+/*
+       Kernel Memory Information structure
+*/
 typedef struct _PVRSRV_KERNEL_MEM_INFO_
 {
-       
+       /* Kernel Mode CPU Virtual address */
        IMG_PVOID                               pvLinAddrKM;
 
-       
+       /* Device Virtual Address */
        IMG_DEV_VIRTADDR                sDevVAddr;
 
-       
+       /* allocation flags */
        IMG_UINT32                              ui32Flags;
 
-       
+       /* Size of the allocated buffer in bytes */
        IMG_SIZE_T                              uAllocSize;
 
-       
+       /* Internal implementation details. Do not use outside services code. */
        PVRSRV_MEMBLK                   sMemBlk;
 
-       
+       /* Address of the backup buffer used in a save/restore of the surface */
        IMG_PVOID                               pvSysBackupBuffer;
 
-       
+       /* refcount for allocation, wrapping and mapping */
        IMG_UINT32                              ui32RefCount;
 
-       
+       /* Set when free call ocured and a mapping was still open */
        IMG_BOOL                                bPendingFree;
 
 
 #if defined(SUPPORT_MEMINFO_IDS)
        #if !defined(USE_CODE)
-       
+       /* Globally unique "stamp" for allocation (not re-used until wrap) */
        IMG_UINT64                              ui64Stamp;
-       #else 
+       #else /* !defined(USE_CODE) */
        IMG_UINT32                              dummy1;
        IMG_UINT32                              dummy2;
-       #endif 
-#endif 
+       #endif /* !defined(USE_CODE) */
+#endif /* defined(SUPPORT_MEMINFO_IDS) */
 
-       
+       /* ptr to associated kernel sync info - NULL if no sync */
        struct _PVRSRV_KERNEL_SYNC_INFO_        *psKernelSyncInfo;
 
        PVRSRV_MEMTYPE                          memType;
 
-    
-
-
-
-
-
-
+    /*
+      To activate the "share mem workaround", add PVRSRV_MEM_XPROC to
+      the flags for the allocation.  This will cause the "map" API to
+      call use Alloc Device Mem but will share the underlying memory
+      block and sync data.  Note that this is a workaround for a bug
+      exposed by a specific use-case on a particular platform.  Do not
+      use this functionality generally.
+    */
        struct {
-        
-
+        /* Record whether the workaround is active for this
+           allocation.  The rest of the fields in this struct are
+           undefined unless this is true */
                IMG_BOOL bInUse;
 
-        
+        /* Store the device cookie handle from the original
+           allocation, as it is not present on the "Map" API. */
                IMG_HANDLE hDevCookieInt;
 
-        
+        /* This is an index into a static array which store
+           information about the underlying allocation */
                IMG_UINT32 ui32ShareIndex;
 
-        
-
+        /* Original arguments as supplied to original
+           "PVRSRVAllocDeviceMem" call, such that a new call to this
+           function can be later constructed */
                IMG_UINT32 ui32OrigReqAttribs;
                IMG_UINT32 ui32OrigReqSize;
                IMG_UINT32 ui32OrigReqAlignment;
@@ -125,78 +166,144 @@ typedef struct _PVRSRV_KERNEL_MEM_INFO_
 } PVRSRV_KERNEL_MEM_INFO;
 
 
+/*
+       Kernel Sync Info structure
+*/
 typedef struct _PVRSRV_KERNEL_SYNC_INFO_
 {
-       
+       /* kernel sync data */
        PVRSRV_SYNC_DATA                *psSyncData;
 
-       
+       /* Device accessible WriteOp Info */
        IMG_DEV_VIRTADDR                sWriteOpsCompleteDevVAddr;
 
-       
+       /* Device accessible ReadOp Info */
        IMG_DEV_VIRTADDR                sReadOpsCompleteDevVAddr;
 
-       
+       /* Device accessible ReadOp Info */
+       IMG_DEV_VIRTADDR                sReadOps2CompleteDevVAddr;
+
+       /* meminfo for sync data */
        PVRSRV_KERNEL_MEM_INFO  *psSyncDataMemInfoKM;
 
-       
-       
-       IMG_UINT32              ui32RefCount;
+       /* Reference count for deferring destruction of syncinfo when it is shared */
+       /* NB: This is only done for devicemem.c (alloc/map/wrap etc), and
+          not (presently) for deviceclass memory */
+       IMG_PVOID              pvRefCount;
 
-       
+       /* Resman cleanup, for those created with explicit API */
        IMG_HANDLE hResItem;
 
-       
+       /* Unique ID of the sync object */
        IMG_UINT32              ui32UID;
 } PVRSRV_KERNEL_SYNC_INFO;
 
+/*!
+ *****************************************************************************
+ *     This is a device addressable version of a pvrsrv_sync_oject
+ *     - any hw cmd may have an unlimited number of these
+ ****************************************************************************/
 typedef struct _PVRSRV_DEVICE_SYNC_OBJECT_
 {
-       
+       /* KEEP THESE 6 VARIABLES TOGETHER FOR UKERNEL BLOCK LOAD */
        IMG_UINT32                      ui32ReadOpsPendingVal;
        IMG_DEV_VIRTADDR        sReadOpsCompleteDevVAddr;
        IMG_UINT32                      ui32WriteOpsPendingVal;
        IMG_DEV_VIRTADDR        sWriteOpsCompleteDevVAddr;
+       IMG_UINT32                      ui32ReadOps2PendingVal;
+       IMG_DEV_VIRTADDR        sReadOps2CompleteDevVAddr;
 } PVRSRV_DEVICE_SYNC_OBJECT;
 
+/*!
+ *****************************************************************************
+ *     encapsulates a single sync object
+ *     - any cmd may have an unlimited number of these
+ ****************************************************************************/
 typedef struct _PVRSRV_SYNC_OBJECT
 {
        PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfoKM;
        IMG_UINT32                              ui32WriteOpsPending;
        IMG_UINT32                              ui32ReadOpsPending;
+       IMG_UINT32                              ui32ReadOps2Pending;
 
 }PVRSRV_SYNC_OBJECT, *PPVRSRV_SYNC_OBJECT;
 
+/*!
+ *****************************************************************************
+ * The `one size fits all' generic command.
+ ****************************************************************************/
 typedef struct _PVRSRV_COMMAND
 {
-       IMG_SIZE_T                      uCmdSize;               
-       IMG_UINT32                      ui32DevIndex;           
-       IMG_UINT32                      CommandType;            
-       IMG_UINT32                      ui32DstSyncCount;       
-       IMG_UINT32                      ui32SrcSyncCount;       
-       PVRSRV_SYNC_OBJECT      *psDstSync;                     
-       PVRSRV_SYNC_OBJECT      *psSrcSync;                     
-       IMG_SIZE_T                      uDataSize;              
-       IMG_UINT32                      ui32ProcessID;          
-       IMG_VOID                        *pvData;                        
+       IMG_SIZE_T                      uCmdSize;               /*!< total size of command */
+       IMG_UINT32                      ui32DevIndex;           /*!< device type - 16bit enum (exported by system) */
+       IMG_UINT32                      CommandType;            /*!< command type */
+       IMG_UINT32                      ui32DstSyncCount;       /*!< number of dst sync objects */
+       IMG_UINT32                      ui32SrcSyncCount;       /*!< number of src sync objects */
+       PVRSRV_SYNC_OBJECT      *psDstSync;                     /*!< dst sync ptr list, allocated on
+                                                               back of this structure, i.e. is resident in Q */
+       PVRSRV_SYNC_OBJECT      *psSrcSync;                     /*!< src sync ptr list, allocated on
+                                                       back of this structure, i.e. is resident in Q */
+       IMG_SIZE_T                      uDataSize;              /*!< Size of Cmd Data Packet
+                                                       - only required in terms of allocating Q space */
+       IMG_UINT32                      ui32ProcessID;          /*!< Process ID for debugging */
+       IMG_VOID                        *pvData;                        /*!< data to be passed to Cmd Handler function,
+                                                       allocated on back of this structure, i.e. is resident in Q */
+       PFN_QUEUE_COMMAND_COMPLETE  pfnCommandComplete; /*!< Command complete callback */
+       IMG_HANDLE                                      hCallbackData;          /*!< Command complete callback data */
 }PVRSRV_COMMAND, *PPVRSRV_COMMAND;
 
 
+/*!
+ *****************************************************************************
+ * Circular command buffer structure forming the queue of pending commands.
+ *
+ * Queues are implemented as circular comamnd buffers (CCBs).
+ * The buffer is allocated as a specified size, plus the size of the largest supported command.
+ * The extra size allows commands to be added without worrying about wrapping around at the end.
+ *
+ * Commands are added to the CCB by client processes and consumed within
+ * kernel mode code running from within  an L/MISR typically.
+ *
+ * The process of adding a command to a queue is as follows:-
+ *     - A `lock' is acquired to prevent other processes from adding commands to a queue
+ *     - Data representing the command to be executed, along with it's PVRSRV_SYNC_INFO
+ *       dependencies is written to the buffer representing the queue at the queues
+ *       current WriteOffset.
+ *     - The PVRSRV_SYNC_INFO that the command depends on are updated to reflect
+ *       the addition of the new command.
+ *     - The WriteOffset is incremented by the size of the command added.
+ *     - If the WriteOffset now lies beyound the declared buffer size, it is
+ *       reset to zero.
+ *     - The semaphore is released.
+ *
+ *****************************************************************************/
 typedef struct _PVRSRV_QUEUE_INFO_
 {
-       IMG_VOID                        *pvLinQueueKM;                  
-       IMG_VOID                        *pvLinQueueUM;                  
-       volatile IMG_SIZE_T     ui32ReadOffset;                 
-       volatile IMG_SIZE_T     ui32WriteOffset;                
-       IMG_UINT32                      *pui32KickerAddrKM;             
-       IMG_UINT32                      *pui32KickerAddrUM;             
-       IMG_SIZE_T                      ui32QueueSize;                  
+       IMG_VOID                        *pvLinQueueKM;                  /*!< Pointer to the command buffer in the kernel's
+                                                                                                address space */
+
+       IMG_VOID                        *pvLinQueueUM;                  /*!< Pointer to the command buffer in the user's
+                                                                                                address space */
+
+       volatile IMG_SIZE_T     ui32ReadOffset;                 /*!< Index into the buffer at which commands are being
+                                                                                                        consumed */
 
-       IMG_UINT32                      ui32ProcessID;                  
+       volatile IMG_SIZE_T     ui32WriteOffset;                /*!< Index into the buffer at which commands are being
+                                                                                                        added */
+
+       IMG_UINT32                      *pui32KickerAddrKM;             /*!< kicker address in the kernel's
+                                                                                                address space*/
+
+       IMG_UINT32                      *pui32KickerAddrUM;             /*!< kicker address in the user's
+                                                                                                address space */
+
+       IMG_SIZE_T                      ui32QueueSize;                  /*!< Size in bytes of the buffer - excluding the safety allocation */
+
+       IMG_UINT32                      ui32ProcessID;                  /*!< Process ID required by resource locking */
 
        IMG_HANDLE                      hMemBlock[2];
 
-       struct _PVRSRV_QUEUE_INFO_ *psNextKM;           
+       struct _PVRSRV_QUEUE_INFO_ *psNextKM;           /*!< The next queue in the system */
 }PVRSRV_QUEUE_INFO;
 
 
@@ -212,62 +319,81 @@ typedef struct _PVRSRV_HEAP_INFO_KM_
 }PVRSRV_HEAP_INFO_KM;
 
 
+/*
+       Event Object information structure
+*/
 typedef struct _PVRSRV_EVENTOBJECT_KM_
 {
-       
+       /* globally unique name of the event object */
        IMG_CHAR        szName[EVENTOBJNAME_MAXLENGTH];
-       
+       /* kernel specific handle for the event object */
        IMG_HANDLE      hOSEventKM;
 
 } PVRSRV_EVENTOBJECT_KM;
 
 
+/*!
+ ******************************************************************************
+ * Structure to retrieve misc. information from services
+ *****************************************************************************/
 typedef struct _PVRSRV_MISC_INFO_KM_
 {
-       IMG_UINT32      ui32StateRequest;               
-       IMG_UINT32      ui32StatePresent;               
+       IMG_UINT32      ui32StateRequest;               /*!< requested State Flags */
+       IMG_UINT32      ui32StatePresent;               /*!< Present/Valid State Flags */
 
-       
+       /*!< SOC Timer register */
        IMG_VOID        *pvSOCTimerRegisterKM;
        IMG_VOID        *pvSOCTimerRegisterUM;
        IMG_HANDLE      hSOCTimerRegisterOSMemHandle;
        IMG_HANDLE      hSOCTimerRegisterMappingInfo;
 
-       
+       /*!< SOC Clock Gating registers */
        IMG_VOID        *pvSOCClockGateRegs;
        IMG_UINT32      ui32SOCClockGateRegsSize;
 
-       
+       /* Memory Stats/DDK version string depending on ui32StateRequest flags */
        IMG_CHAR        *pszMemoryStr;
        IMG_UINT32      ui32MemoryStrLen;
 
-       
-       PVRSRV_EVENTOBJECT_KM   sGlobalEventObject;
+       /* global event object */
+       PVRSRV_EVENTOBJECT_KM   sGlobalEventObject;//FIXME: should be private to services
        IMG_HANDLE                              hOSGlobalEvent;
 
-       
+       /* Note: add misc. items as required */
        IMG_UINT32      aui32DDKVersion[4];
 
-       
+       /*!< CPU cache flush controls: */
        struct
        {
-               
+               /*!< Defer the CPU cache op to the next HW op to be submitted (else flush now) */
                IMG_BOOL bDeferOp;
 
-               
+               /*!< Type of cache operation to perform */
                PVRSRV_MISC_INFO_CPUCACHEOP_TYPE eCacheOpType;
 
+               /*!< Meminfo (or meminfo handle) to flush */
                PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo;
 
-               
+               /*!< Offset in MemInfo to start cache op */
                IMG_VOID *pvBaseVAddr;
 
-               
+               /*!< Length of range to perform cache op  */
                IMG_UINT32      ui32Length;
        } sCacheOpCtl;
+
+       /*!< Meminfo refcount controls: */
+       struct
+       {
+               /*!< Meminfo (or meminfo handle) to get refcount for */
+               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo;
+
+               /*!< Resulting refcount */
+               IMG_UINT32 ui32RefCount;
+       } sGetRefCountCtl;
 } PVRSRV_MISC_INFO_KM;
 
 
+/* insert command function pointer */
 typedef PVRSRV_ERROR (*PFN_INSERT_CMD) (PVRSRV_QUEUE_INFO*,
                                                                                PVRSRV_COMMAND**,
                                                                                IMG_UINT32,
@@ -277,9 +403,18 @@ typedef PVRSRV_ERROR (*PFN_INSERT_CMD) (PVRSRV_QUEUE_INFO*,
                                                                                IMG_UINT32,
                                                                                PVRSRV_KERNEL_SYNC_INFO*[],
                                                                                IMG_UINT32);
+/* submit command function pointer */
 typedef PVRSRV_ERROR (*PFN_SUBMIT_CMD) (PVRSRV_QUEUE_INFO*, PVRSRV_COMMAND*, IMG_BOOL);
 
 
+/***********************************************************************
+       Device Class Structures
+***********************************************************************/
+
+/*
+       Generic Device Class Buffer
+       - details common between DC and BC
+*/
 typedef struct PVRSRV_DEVICECLASS_BUFFER_TAG
 {
        PFN_GET_BUFFER_ADDR             pfnGetBufferAddr;
@@ -291,6 +426,9 @@ typedef struct PVRSRV_DEVICECLASS_BUFFER_TAG
 } PVRSRV_DEVICECLASS_BUFFER;
 
 
+/*
+       Common Device Class client services information structure
+*/
 typedef struct PVRSRV_CLIENT_DEVICECLASS_INFO_TAG
 {
 #if defined (SUPPORT_SID_INTERFACE)
@@ -302,68 +440,99 @@ typedef struct PVRSRV_CLIENT_DEVICECLASS_INFO_TAG
 } PVRSRV_CLIENT_DEVICECLASS_INFO;
 
 
-#ifdef INLINE_IS_PRAGMA
-#pragma inline(PVRSRVGetWriteOpsPending)
-#endif
-static INLINE
-IMG_UINT32 PVRSRVGetWriteOpsPending(PVRSRV_KERNEL_SYNC_INFO *psSyncInfo, IMG_BOOL bIsReadOp)
+typedef enum
 {
-       IMG_UINT32 ui32WriteOpsPending;
-
-       if(bIsReadOp)
-       {
-               ui32WriteOpsPending = psSyncInfo->psSyncData->ui32WriteOpsPending;
-       }
-       else
-       {
-               
-
-
-               ui32WriteOpsPending = psSyncInfo->psSyncData->ui32WriteOpsPending++;
-       }
-
-       return ui32WriteOpsPending;
+       PVRSRV_FREE_CALLBACK_ORIGIN_ALLOCATOR,
+       PVRSRV_FREE_CALLBACK_ORIGIN_IMPORTER,
+       PVRSRV_FREE_CALLBACK_ORIGIN_EXTERNAL,
 }
+PVRSRV_FREE_CALLBACK_ORIGIN;
 
-#ifdef INLINE_IS_PRAGMA
-#pragma inline(PVRSRVGetReadOpsPending)
-#endif
-static INLINE
-IMG_UINT32 PVRSRVGetReadOpsPending(PVRSRV_KERNEL_SYNC_INFO *psSyncInfo, IMG_BOOL bIsReadOp)
-{
-       IMG_UINT32 ui32ReadOpsPending;
 
-       if(bIsReadOp)
-       {
-               ui32ReadOpsPending = psSyncInfo->psSyncData->ui32ReadOpsPending++;
-       }
-       else
-       {
-               ui32ReadOpsPending = psSyncInfo->psSyncData->ui32ReadOpsPending;
-       }
+IMG_IMPORT
+PVRSRV_ERROR FreeMemCallBackCommon(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
+                                   IMG_UINT32 ui32Param,
+                                   PVRSRV_FREE_CALLBACK_ORIGIN eCallbackOrigin);
 
-       return ui32ReadOpsPending;
-}
 
 IMG_IMPORT
 PVRSRV_ERROR PVRSRVQueueCommand(IMG_HANDLE hQueueInfo,
                                                                PVRSRV_COMMAND *psCommand);
 
 
+/*!
+ * *****************************************************************************
+ * @Description Allocates system memory on behalf of a userspace process that is
+ *               addressable by the kernel; suitable for mapping into the current
+ *        user space process; suitable for mapping into other userspace
+ *        processes and it is possible to entirely disassociate the system
+ *        memory from the current userspace process via a call to
+ *        PVRSRVDissociateSharedSysMemoryKM.
+ *
+ * @Input psConnection
+ * @Input ui32Flags
+ * @Input ui32Size
+ * @Output ppsClientMemInfo
+ *
+ * @Return PVRSRV_ERROR
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV
 PVRSRVAllocSharedSysMem(const PVRSRV_CONNECTION *psConnection,
                                                IMG_UINT32 ui32Flags,
                                                IMG_SIZE_T ui32Size,
                                                PVRSRV_CLIENT_MEM_INFO **ppsClientMemInfo);
 
+/*!
+ * *****************************************************************************
+ * @Description Frees memory allocated via PVRSRVAllocSharedMemory (Note you must
+ *        be sure any additional kernel references you created have been
+ *        removed before freeing the memory)
+ *
+ * @Input psConnection
+ * @Input psClientMemInfo
+ *
+ * @Return PVRSRV_ERROR
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV
 PVRSRVFreeSharedSysMem(const PVRSRV_CONNECTION *psConnection,
                                           PVRSRV_CLIENT_MEM_INFO *psClientMemInfo);
 
+/*!
+ * *****************************************************************************
+ * @Description Removes any userspace reference to the shared system memory, except
+ *        that the memory will remain registered with the services resource
+ *        manager so if the process dies/exits the actuall shared memory will
+ *        still be freed.
+ *        If you need to move ownership of shared memory from userspace
+ *        to kernel space then before unrefing a shared piece of memory you can
+ *        take a copy of psClientMemInfo->hKernelMemInfo; call
+ *        PVRSRVUnrefSharedSysMem; then use some mechanism (specialised bridge
+ *        function) to request that the kernel remove any resource manager
+ *        reference to the shared memory and assume responsaility for the meminfo
+ *        in one atomic operation. (Note to aid with such a kernel space bridge
+ *        function see PVRSRVDissociateSharedSysMemoryKM)
+ *
+ * @Input psConnection
+ * @Input psClientMemInfo
+ *
+ * @Return PVRSRV_ERROR
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR
 PVRSRVUnrefSharedSysMem(const PVRSRV_CONNECTION *psConnection,
                         PVRSRV_CLIENT_MEM_INFO *psClientMemInfo);
 
+/*!
+ * *****************************************************************************
+ * @Description For shared system or device memory that is owned by the kernel, you can
+ *              use this function to map the underlying memory into a client using a
+ *              handle for the KernelMemInfo.
+ *
+ * @Input psConnection
+ * @Input hKernelMemInfo
+ * @Output ppsClientMemInfo
+ *
+ * @Return PVRSRV_ERROR
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV
 PVRSRVMapMemInfoMem(const PVRSRV_CONNECTION *psConnection,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -377,5 +546,8 @@ PVRSRVMapMemInfoMem(const PVRSRV_CONNECTION *psConnection,
 #if defined (__cplusplus)
 }
 #endif
-#endif 
+#endif /* __SERVICESINT_H__ */
 
+/*****************************************************************************
+ End of file (servicesint.h)
+*****************************************************************************/
index ec630a5..33b27e3 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX Bridge Functionality
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Header for the sgx Brdige code
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined(__SGX_BRIDGE_H__)
 #define __SGX_BRIDGE_H__
@@ -40,6 +56,14 @@ extern "C" {
 #endif
 
 
+/* 
+ * Bridge Cmd Ids
+ */
+
+/* *REMEMBER* to update PVRSRV_BRIDGE_LAST_SGX_CMD if you add/remove a command! 
+ * Also you need to ensure all PVRSRV_BRIDGE_SGX_CMD_BASE+ offsets are sequential!
+ */
+
 #define PVRSRV_BRIDGE_SGX_CMD_BASE (PVRSRV_BRIDGE_LAST_NON_DEVICE_CMD+1)
 #define PVRSRV_BRIDGE_SGX_GETCLIENTINFO                        PVRSRV_IOWR(PVRSRV_BRIDGE_SGX_CMD_BASE+0)
 #define PVRSRV_BRIDGE_SGX_RELEASECLIENTINFO            PVRSRV_IOWR(PVRSRV_BRIDGE_SGX_CMD_BASE+1)
@@ -88,17 +112,30 @@ extern "C" {
 
 
 
+/* *REMEMBER* to update PVRSRV_BRIDGE_LAST_SGX_CMD if you add/remove a command! 
+ * You need to ensure all PVRSRV_BRIDGE_SGX_CMD_BASE+ offsets are sequential!
+ */
 #define PVRSRV_BRIDGE_LAST_SGX_CMD (PVRSRV_BRIDGE_SGX_CMD_BASE+37)
 
+/*****************************************************************************
+ * Input structures for IOCTL/DRVESC 
+ *****************************************************************************/
+
+/*!
+ *****************************************************************************
+ *     `bridge in' SGX Get Phys Page Addr
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_GETPHYSPAGEADDR
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_HANDLE hDevMemHeap;
        IMG_DEV_VIRTADDR sDevVAddr;
 }PVRSRV_BRIDGE_IN_GETPHYSPAGEADDR;
 
+/*!
+ *****************************************************************************
+ *     `bridge out' SGX Get Phys Page Addr
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_OUT_GETPHYSPAGEADDR
 {
        PVRSRV_ERROR            eError;
@@ -106,10 +143,13 @@ typedef struct PVRSRV_BRIDGE_OUT_GETPHYSPAGEADDR
        IMG_CPU_PHYADDR         CpuPAddr;
 }PVRSRV_BRIDGE_OUT_GETPHYSPAGEADDR;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' set transfer context priority
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_SGX_SET_TRANSFER_CONTEXT_PRIORITY_TAG
  {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
  #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
        IMG_SID                                 hHWTransferContext;
@@ -121,10 +161,13 @@ typedef struct PVRSRV_BRIDGE_IN_SGX_SET_TRANSFER_CONTEXT_PRIORITY_TAG
     IMG_UINT32              ui32OffsetOfPriorityField;
 }PVRSRV_BRIDGE_IN_SGX_SET_TRANSFER_CONTEXT_PRIORITY;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' set render context priority
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_SGX_SET_RENDER_CONTEXT_PRIORITY_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
        IMG_SID                                 hHWRenderContext;
@@ -136,10 +179,13 @@ typedef struct PVRSRV_BRIDGE_IN_SGX_SET_RENDER_CONTEXT_PRIORITY_TAG
     IMG_UINT32              ui32OffsetOfPriorityField;
 }PVRSRV_BRIDGE_IN_SGX_SET_RENDER_CONTEXT_PRIORITY;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' Get Client Info
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_GETCLIENTINFO_TAG
 {
-       IMG_UINT32                                      ui32BridgeFlags; 
+       IMG_UINT32                                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                         hDevCookie;
 #else
@@ -147,17 +193,23 @@ typedef struct PVRSRV_BRIDGE_IN_GETCLIENTINFO_TAG
 #endif
 }PVRSRV_BRIDGE_IN_GETCLIENTINFO;
 
+/*!
+ *****************************************************************************
+ *     `bridge out' Get internal device info
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_OUT_GETINTERNALDEVINFO_TAG
 {
        SGX_INTERNAL_DEVINFO    sSGXInternalDevInfo;
        PVRSRV_ERROR                            eError;
 }PVRSRV_BRIDGE_OUT_GETINTERNALDEVINFO;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' Get internal device info
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_GETINTERNALDEVINFO_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
 #else
@@ -165,17 +217,23 @@ typedef struct PVRSRV_BRIDGE_IN_GETINTERNALDEVINFO_TAG
 #endif
 }PVRSRV_BRIDGE_IN_GETINTERNALDEVINFO;
 
+/*!
+ *****************************************************************************
+ *     `bridge out' Get Client Info
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_OUT_GETCLIENTINFO_TAG
 {
        SGX_CLIENT_INFO         sClientInfo;
        PVRSRV_ERROR                    eError;
 }PVRSRV_BRIDGE_OUT_GETCLIENTINFO;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' Release Client Info
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_RELEASECLIENTINFO_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
 #else
@@ -184,10 +242,13 @@ typedef struct PVRSRV_BRIDGE_IN_RELEASECLIENTINFO_TAG
        SGX_CLIENT_INFO         sClientInfo;
 }PVRSRV_BRIDGE_IN_RELEASECLIENTINFO;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' Pdump ISP mem Pol
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_ISPBREAKPOLL_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
 #else
@@ -195,10 +256,13 @@ typedef struct PVRSRV_BRIDGE_IN_ISPBREAKPOLL_TAG
 #endif
 }PVRSRV_BRIDGE_IN_ISPBREAKPOLL;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' KickTA
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_DOKICK_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
 #else
@@ -207,10 +271,13 @@ typedef struct PVRSRV_BRIDGE_IN_DOKICK_TAG
        SGX_CCB_KICK                    sCCBKick;
 }PVRSRV_BRIDGE_IN_DOKICK;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' SGXScheduleProcessQueues
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_SGX_SCHEDULE_PROCESS_QUEUES_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
 #else
@@ -220,10 +287,13 @@ typedef struct PVRSRV_BRIDGE_IN_SGX_SCHEDULE_PROCESS_QUEUES_TAG
 
 
 #if defined(TRANSFER_QUEUE)
+/*!
+ *****************************************************************************
+ *     `bridge in' SubmitTransfer
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_SUBMITTRANSFER_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
 #else
@@ -233,10 +303,13 @@ typedef struct PVRSRV_BRIDGE_IN_SUBMITTRANSFER_TAG
 }PVRSRV_BRIDGE_IN_SUBMITTRANSFER;
 
 #if defined(SGX_FEATURE_2D_HARDWARE)
+/*!
+ *****************************************************************************
+ *     `bridge in' Submit2D
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_SUBMIT2D_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
 #else
@@ -247,10 +320,13 @@ typedef struct PVRSRV_BRIDGE_IN_SUBMIT2D_TAG
 #endif
 #endif
 
+/*!
+ *****************************************************************************
+ *     `bridge in' ReadRegistryString
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_READREGDWORD_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
 #else
@@ -260,7 +336,10 @@ typedef struct PVRSRV_BRIDGE_IN_READREGDWORD_TAG
     IMG_PCHAR                          pszValue;
 }PVRSRV_BRIDGE_IN_READREGDWORD;
 
+/*!
+ *****************************************************************************
+ *     `bridge out' ReadRegistryString
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_OUT_READREGDWORD_TAG
 {
        PVRSRV_ERROR    eError;
@@ -268,9 +347,13 @@ typedef struct PVRSRV_BRIDGE_OUT_READREGDWORD_TAG
 }PVRSRV_BRIDGE_OUT_READREGDWORD;
 
 
+/*!
+ *****************************************************************************
+ *     `bridge in' SGXGetMiscInfo
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_SGXGETMISCINFO_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDevCookie;
 #else
@@ -279,9 +362,13 @@ typedef struct PVRSRV_BRIDGE_IN_SGXGETMISCINFO_TAG
        SGX_MISC_INFO   *psMiscInfo;
 }PVRSRV_BRIDGE_IN_SGXGETMISCINFO;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' SGXGetInfoForSrvInit
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_SGXINFO_FOR_SRVINIT_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDevCookie;
 #else
@@ -289,15 +376,23 @@ typedef struct PVRSRV_BRIDGE_IN_SGXINFO_FOR_SRVINIT_TAG
 #endif
 }PVRSRV_BRIDGE_IN_SGXINFO_FOR_SRVINIT;
 
+/*!
+ *****************************************************************************
+ *     `bridge out' SGXGetInfoForSrvInit
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_SGXINFO_FOR_SRVINIT_TAG
 {
        PVRSRV_ERROR                    eError;
        SGX_BRIDGE_INFO_FOR_SRVINIT     sInitInfo;
 }PVRSRV_BRIDGE_OUT_SGXINFO_FOR_SRVINIT;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' SGXDevInitPart2
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_SGXDEVINITPART2_TAG
 {
-       IMG_UINT32              ui32BridgeFlags; 
+       IMG_UINT32              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 hDevCookie;
 #else
@@ -306,6 +401,10 @@ typedef struct PVRSRV_BRIDGE_IN_SGXDEVINITPART2_TAG
        SGX_BRIDGE_INIT_INFO    sInitInfo;
 }PVRSRV_BRIDGE_IN_SGXDEVINITPART2;
 
+/*!
+ *****************************************************************************
+ *     `bridge out' SGXDevInitPart2
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_SGXDEVINITPART2_TAG
 {
        PVRSRV_ERROR    eError;
@@ -313,10 +412,13 @@ typedef struct PVRSRV_BRIDGE_OUT_SGXDEVINITPART2_TAG
 
 }PVRSRV_BRIDGE_OUT_SGXDEVINITPART2;
 
+/*!
+ *****************************************************************************
+ *     `bridge in' 2D query blits complete
+ *****************************************************************************/ 
 typedef struct PVRSRV_BRIDGE_IN_2DQUERYBLTSCOMPLETE_TAG
 {
-       IMG_UINT32                              ui32BridgeFlags; 
+       IMG_UINT32                              ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                 hDevCookie;
        IMG_SID                                 hKernSyncInfo;
@@ -332,7 +434,7 @@ typedef struct PVRSRV_BRIDGE_IN_2DQUERYBLTSCOMPLETE_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SGXFINDSHAREDPBDESC_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -367,7 +469,7 @@ typedef struct PVRSRV_BRIDGE_OUT_SGXFINDSHAREDPBDESC_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SGXUNREFSHAREDPBDESC_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hSharedPBDesc;
 #else
@@ -383,7 +485,7 @@ typedef struct PVRSRV_BRIDGE_OUT_SGXUNREFSHAREDPBDESC_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SGXADDSHAREDPBDESC_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_UINT32 ui32TotalPBSize;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
@@ -418,7 +520,7 @@ typedef struct PVRSRV_BRIDGE_OUT_SGXADDSHAREDPBDESC_TAG
 #ifdef PDUMP
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_BUFFER_ARRAY_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        SGX_KICKTA_DUMP_BUFFER *psBufferArray;
        IMG_UINT32 ui32BufferArrayLength;
        IMG_BOOL bDumpPolls;
@@ -426,7 +528,7 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_BUFFER_ARRAY_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_3D_SIGNATURE_REGISTERS_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
        IMG_SID    hDevMemContext;
@@ -442,7 +544,7 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_3D_SIGNATURE_REGISTERS_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_PDUMPCOUNTER_REGISTERS_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -456,7 +558,7 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMPCOUNTER_REGISTERS_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_TA_SIGNATURE_REGISTERS_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -471,7 +573,7 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_TA_SIGNATURE_REGISTERS_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_HWPERFCB_TAG
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
        IMG_SID                         hDevMemContext;
@@ -487,7 +589,7 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_HWPERFCB_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_PDUMP_SAVEMEM
 {
-       IMG_UINT32                      ui32BridgeFlags; 
+       IMG_UINT32                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         hDevCookie;
        IMG_SID                         hDevMemContext;
@@ -509,7 +611,7 @@ typedef struct PVRSRV_BRIDGE_IN_PDUMP_SAVEMEM
 
 typedef struct PVRSRV_BRIDGE_IN_SGX_REGISTER_HW_RENDER_CONTEXT_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -534,7 +636,7 @@ typedef struct PVRSRV_BRIDGE_OUT_SGX_REGISTER_HW_RENDER_CONTEXT_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SGX_UNREGISTER_HW_RENDER_CONTEXT_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_BOOL   bForceCleanup;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
@@ -547,7 +649,7 @@ typedef struct PVRSRV_BRIDGE_IN_SGX_UNREGISTER_HW_RENDER_CONTEXT_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SGX_REGISTER_HW_TRANSFER_CONTEXT_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -572,7 +674,7 @@ typedef struct PVRSRV_BRIDGE_OUT_SGX_REGISTER_HW_TRANSFER_CONTEXT_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SGX_UNREGISTER_HW_TRANSFER_CONTEXT_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_BOOL   bForceCleanup;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
@@ -585,7 +687,7 @@ typedef struct PVRSRV_BRIDGE_IN_SGX_UNREGISTER_HW_TRANSFER_CONTEXT_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SGX_FLUSH_HW_RENDER_TARGET_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -594,11 +696,14 @@ typedef struct PVRSRV_BRIDGE_IN_SGX_FLUSH_HW_RENDER_TARGET_TAG
        IMG_DEV_VIRTADDR sHWRTDataSetDevVAddr;
 }PVRSRV_BRIDGE_IN_SGX_FLUSH_HW_RENDER_TARGET;
 
+/*!
+ *****************************************************************************
+ *     SGX 2D specific defines
+ *****************************************************************************/ 
 #if defined(SGX_FEATURE_2D_HARDWARE)
 typedef struct PVRSRV_BRIDGE_IN_SGX_REGISTER_HW_2D_CONTEXT_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
 #else
@@ -623,7 +728,7 @@ typedef struct PVRSRV_BRIDGE_OUT_SGX_REGISTER_HW_2D_CONTEXT_TAG
 
 typedef struct PVRSRV_BRIDGE_IN_SGX_UNREGISTER_HW_2D_CONTEXT_TAG
 {
-       IMG_UINT32 ui32BridgeFlags; 
+       IMG_UINT32 ui32BridgeFlags; /* Must be first member of structure */
        IMG_BOOL   bForceCleanup;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID    hDevCookie;
@@ -634,13 +739,17 @@ typedef struct PVRSRV_BRIDGE_IN_SGX_UNREGISTER_HW_2D_CONTEXT_TAG
 #endif
 }PVRSRV_BRIDGE_IN_SGX_UNREGISTER_HW_2D_CONTEXT;
 
-#define        SGX2D_MAX_BLT_CMD_SIZ           256     
-#endif 
+#define        SGX2D_MAX_BLT_CMD_SIZ           256     /* Maximum size of a blit command, in bytes */
+#endif /* SGX_FEATURE_2D_HARDWARE */
 
 
+/*!
+ *****************************************************************************
+ *     `bridge in' SGXReadHWPerfCB
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_IN_SGX_READ_HWPERF_CB_TAG
 {
-       IMG_UINT32                                      ui32BridgeFlags; 
+       IMG_UINT32                                      ui32BridgeFlags; /* Must be first member of structure */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                                         hDevCookie;
 #else
@@ -650,6 +759,10 @@ typedef struct PVRSRV_BRIDGE_IN_SGX_READ_HWPERF_CB_TAG
        PVRSRV_SGX_HWPERF_CB_ENTRY      *psHWPerfCBData;
 } PVRSRV_BRIDGE_IN_SGX_READ_HWPERF_CB;
 
+/*!
+ *****************************************************************************
+ *     `bridge out' SGXReadHWPerfCB
+ *****************************************************************************/
 typedef struct PVRSRV_BRIDGE_OUT_SGX_READ_HWPERF_CB_TAG
 {
        PVRSRV_ERROR            eError;
@@ -662,5 +775,5 @@ typedef struct PVRSRV_BRIDGE_OUT_SGX_READ_HWPERF_CB_TAG
 }
 #endif
 
-#endif 
+#endif /* __SGX_BRIDGE_H__ */
 
index d5cffdb..3a9866f 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX microkernel interface structures used by srvkm
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    SGX microkernel interface structures used by srvkm
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined (__SGX_MKIF_KM_H__)
 #define __SGX_MKIF_KM_H__
@@ -33,6 +49,7 @@
 
 
 #if !defined (SGX_MP_CORE_SELECT)
+/* MP register control macros */
 #if defined(SGX_FEATURE_MP)
        #define SGX_REG_BANK_SHIFT                      (14)
        #define SGX_REG_BANK_SIZE                       (1 << SGX_REG_BANK_SHIFT)
        #define SGX_MP_MASTER_SELECT(x)         (x + (SGX_REG_BANK_MASTER_INDEX * SGX_REG_BANK_SIZE))
 #else
        #define SGX_MP_CORE_SELECT(x,i)         (x)
-#endif 
+#endif /* SGX_FEATURE_MP */
 #endif
 
 
+/*!
+ ******************************************************************************
+ * CCB command structure for SGX
+ *****************************************************************************/
 typedef struct _SGXMKIF_COMMAND_
 {
-       IMG_UINT32                              ui32ServiceAddress;             
-       IMG_UINT32                              ui32CacheControl;               
-       IMG_UINT32                              ui32Data[6];                    
+       IMG_UINT32                              ui32ServiceAddress;             /*!< address of the USE command handler */
+       IMG_UINT32                              ui32CacheControl;               /*!< See SGXMKIF_CC_INVAL_* */
+       IMG_UINT32                              ui32Data[6];                    /*!< array of other command control words */
 } SGXMKIF_COMMAND;
 
 
+/*!
+ ******************************************************************************
+ * CCB array of commands for SGX
+ *****************************************************************************/
 typedef struct _PVRSRV_SGX_KERNEL_CCB_
 {
-       SGXMKIF_COMMAND         asCommands[256];                
+       SGXMKIF_COMMAND         asCommands[256];                /*!< array of commands */
 } PVRSRV_SGX_KERNEL_CCB;
 
 
+/*!
+ ******************************************************************************
+ * CCB control for SGX
+ *****************************************************************************/
 typedef struct _PVRSRV_SGX_CCB_CTL_
 {
-       IMG_UINT32                              ui32WriteOffset;                
-       IMG_UINT32                              ui32ReadOffset;                 
+       IMG_UINT32                              ui32WriteOffset;                /*!< write offset into array of commands (MUST be alligned to 16 bytes!) */
+       IMG_UINT32                              ui32ReadOffset;                 /*!< read offset into array of commands */
 } PVRSRV_SGX_CCB_CTL;
 
 
+/*!
+ *****************************************************************************
+ * Control data for SGX
+ *****************************************************************************/
 typedef struct _SGXMKIF_HOST_CTL_
 {
 #if defined(PVRSRV_USSE_EDM_BREAKPOINTS)
@@ -74,44 +107,57 @@ typedef struct _SGXMKIF_HOST_CTL_
        IMG_UINT32                              ui32Continue;
 #endif
 
-       volatile IMG_UINT32             ui32InitStatus;                         
-       volatile IMG_UINT32             ui32PowerStatus;                        
-       volatile IMG_UINT32             ui32CleanupStatus;                      
+       volatile IMG_UINT32             ui32InitStatus;                         /*!< Microkernel Initialisation status */
+       volatile IMG_UINT32             ui32PowerStatus;                        /*!< Microkernel Power Management status */
+       volatile IMG_UINT32             ui32CleanupStatus;                      /*!< Microkernel Resource Management status */
 #if defined(FIX_HW_BRN_28889)
-       volatile IMG_UINT32             ui32InvalStatus;                        
+       volatile IMG_UINT32             ui32InvalStatus;                        /*!< Microkernel BIF Cache Invalidate status */
 #endif
 #if defined(SUPPORT_HW_RECOVERY)
-       IMG_UINT32                              ui32uKernelDetectedLockups;     
-       IMG_UINT32                              ui32HostDetectedLockups;        
-       IMG_UINT32                              ui32HWRecoverySampleRate;       
-#endif 
-       IMG_UINT32                              ui32uKernelTimerClock;          
-       IMG_UINT32                              ui32ActivePowManSampleRate;     
-       IMG_UINT32                              ui32InterruptFlags;             
-       IMG_UINT32                              ui32InterruptClearFlags;        
-       IMG_UINT32                              ui32BPSetClearSignal;           
-
-       IMG_UINT32                              ui32NumActivePowerEvents;       
-
-       IMG_UINT32                              ui32TimeWraps;                          
-       IMG_UINT32                              ui32HostClock;                          
-       IMG_UINT32                              ui32AssertFail;                         
+       IMG_UINT32                              ui32uKernelDetectedLockups;     /*!< counter relating to the number of lockups the uKernel has detected */
+       IMG_UINT32                              ui32HostDetectedLockups;        /*!< counter relating to the number of lockups the host has detected */
+       IMG_UINT32                              ui32HWRecoverySampleRate;       /*!< SGX lockup detection rate (in multiples of the timer period) */
+#endif /* SUPPORT_HW_RECOVERY*/
+       IMG_UINT32                              ui32uKernelTimerClock;          /*!< SGX ukernel timer period (in clocks) */
+       IMG_UINT32                              ui32ActivePowManSampleRate;     /*!< SGX Active Power latency period (in multiples of the timer period) */
+       IMG_UINT32                              ui32InterruptFlags;             /*!< Interrupt flags - PVRSRV_USSE_EDM_INTERRUPT_xxx */
+       IMG_UINT32                              ui32InterruptClearFlags;        /*!< Interrupt clear flags - PVRSRV_USSE_EDM_INTERRUPT_xxx */
+       IMG_UINT32                              ui32BPSetClearSignal;           /*!< Breakpoint set/cear signal */
+
+       IMG_UINT32                              ui32NumActivePowerEvents;       /*!< counter for the number of active power events */
+
+       IMG_UINT32                              ui32TimeWraps;                          /*!< to count time wraps in the Timer task*/
+       IMG_UINT32                              ui32HostClock;                          /*!< Host clock value at microkernel power-up time */
+       IMG_UINT32                              ui32AssertFail;                         /*!< Microkernel assert failure code */
 
 #if defined(SGX_FEATURE_EXTENDED_PERF_COUNTERS)
-       IMG_UINT32                              aui32PerfGroup[PVRSRV_SGX_HWPERF_NUM_COUNTERS]; 
-       IMG_UINT32                              aui32PerfBit[PVRSRV_SGX_HWPERF_NUM_COUNTERS];   
+       IMG_UINT32                              aui32PerfGroup[PVRSRV_SGX_HWPERF_NUM_COUNTERS]; /*!< Specifies the HW's active group selectors */
+       IMG_UINT32                              aui32PerfBit[PVRSRV_SGX_HWPERF_NUM_COUNTERS];   /*!< Specifies the HW's active bit selectors */
+       IMG_UINT32                              ui32PerfCounterBitSelect;                                               /*!< Specifies the HW's counter bit selectors */
+       IMG_UINT32                              ui32PerfSumMux;                                                                 /*!< Specifies the HW's sum_mux selectors */
 #else
-       IMG_UINT32                              ui32PerfGroup;                                                                  
-#endif 
+       IMG_UINT32                              ui32PerfGroup;                                                                  /*!< Specifies the HW's active group */
+#endif /* SGX_FEATURE_EXTENDED_PERF_COUNTERS */
 
 #if defined(FIX_HW_BRN_31939)
        IMG_UINT32                              ui32BRN31939Mem;
 #endif
 
-       IMG_UINT32                              ui32OpenCLDelayCount;                   
+       IMG_UINT32                              ui32OpenCLDelayCount;                   /* Counter to keep track OpenCL task completion time in units of regular task time out events */
 } SGXMKIF_HOST_CTL;
 
+/*
+ * TA queue Kick flags
+ */
+/* Set in DoKickKM to indicate the command is ready to be processed */
 #define        SGXMKIF_CMDTA_CTRLFLAGS_READY                   0x00000001
+/*!
+ ******************************************************************************
+ * Shared TA command structure.
+ * This structure is part of the TA command structure proper (SGXMKIF_CMDTA),
+ * and is accessed from the kernel part of the driver and the microkernel.
+ * There shouldn't be a need to access it from user space.
+ *****************************************************************************/
 typedef struct _SGXMKIF_CMDTA_SHARED_
 {
        IMG_UINT32                      ui32CtrlFlags;
@@ -119,21 +165,23 @@ typedef struct _SGXMKIF_CMDTA_SHARED_
        IMG_UINT32                      ui32NumTAStatusVals;
        IMG_UINT32                      ui32Num3DStatusVals;
 
-       
+       /* KEEP THESE 4 VARIABLES TOGETHER FOR UKERNEL BLOCK LOAD */
        IMG_UINT32                      ui32TATQSyncWriteOpsPendingVal;
        IMG_DEV_VIRTADDR        sTATQSyncWriteOpsCompleteDevVAddr;
        IMG_UINT32                      ui32TATQSyncReadOpsPendingVal;
        IMG_DEV_VIRTADDR        sTATQSyncReadOpsCompleteDevVAddr;
 
-       
+       /* KEEP THESE 4 VARIABLES TOGETHER FOR UKERNEL BLOCK LOAD */
        IMG_UINT32                      ui323DTQSyncWriteOpsPendingVal;
        IMG_DEV_VIRTADDR        s3DTQSyncWriteOpsCompleteDevVAddr;
        IMG_UINT32                      ui323DTQSyncReadOpsPendingVal;
        IMG_DEV_VIRTADDR        s3DTQSyncReadOpsCompleteDevVAddr;
 
+       /* sync criteria used for TA/3D dependency synchronisation */
+       PVRSRV_DEVICE_SYNC_OBJECT       sTA3DDependency;
 
 #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS)
-       
+       /* SRC and DST syncs */
        IMG_UINT32                                      ui32NumTASrcSyncs;
        PVRSRV_DEVICE_SYNC_OBJECT       asTASrcSyncs[SGX_MAX_TA_SRC_SYNCS];
        IMG_UINT32                                      ui32NumTADstSyncs;
@@ -141,47 +189,61 @@ typedef struct _SGXMKIF_CMDTA_SHARED_
        IMG_UINT32                                      ui32Num3DSrcSyncs;
        PVRSRV_DEVICE_SYNC_OBJECT       as3DSrcSyncs[SGX_MAX_3D_SRC_SYNCS];
 #else
-       
+       /* source dependency details */
        IMG_UINT32                      ui32NumSrcSyncs;
-       PVRSRV_DEVICE_SYNC_OBJECT       asSrcSyncs[SGX_MAX_SRC_SYNCS];
+       PVRSRV_DEVICE_SYNC_OBJECT       asSrcSyncs[SGX_MAX_SRC_SYNCS_TA];
 #endif
 
-       
-       PVRSRV_DEVICE_SYNC_OBJECT       sTA3DDependency;
-
        CTL_STATUS                      sCtlTAStatusInfo[SGX_MAX_TA_STATUS_VALS];
        CTL_STATUS                      sCtl3DStatusInfo[SGX_MAX_3D_STATUS_VALS];
 
 } SGXMKIF_CMDTA_SHARED;
 
+/*
+ * Services internal TQ limits
+ */
 #define SGXTQ_MAX_STATUS                                               SGX_MAX_TRANSFER_STATUS_VALS + 2
 
+/*
+ * Transfer queue Kick flags
+ */
+/* if set the uKernel won't update the sync objects on completion*/
 #define SGXMKIF_TQFLAGS_NOSYNCUPDATE                   0x00000001
+/* if set the kernel won't advance the pending values*/
 #define SGXMKIF_TQFLAGS_KEEPPENDING                            0x00000002
+/* in services equivalent for the same client flags*/
 #define SGXMKIF_TQFLAGS_TATQ_SYNC                              0x00000004
 #define SGXMKIF_TQFLAGS_3DTQ_SYNC                              0x00000008
 #if defined(SGX_FEATURE_FAST_RENDER_CONTEXT_SWITCH)
 #define SGXMKIF_TQFLAGS_CTXSWITCH                              0x00000010
 #endif
+/* if set uKernel only updates syncobjects / status values*/
 #define SGXMKIF_TQFLAGS_DUMMYTRANSFER                  0x00000020
 
+/*!
+ ******************************************************************************
+ * Shared Transfer Queue command structure.
+ * This structure is placed at the start of the TQ command structure proper
+ * (SGXMKIF_TRANSFERCMD), and is accessed from the kernel part of the driver
+ * and the microkernel.
+ *****************************************************************************/
 typedef struct _SGXMKIF_TRANSFERCMD_SHARED_
 {
-       
+       /* need to be able to check read and write ops on src, and update reads */
 
        IMG_UINT32                      ui32NumSrcSyncs;
-       PVRSRV_DEVICE_SYNC_OBJECT       asSrcSyncs[SGX_MAX_SRC_SYNCS];
-       
+       PVRSRV_DEVICE_SYNC_OBJECT       asSrcSyncs[SGX_MAX_SRC_SYNCS_TQ];
+       /* need to be able to check reads and writes on dest, and update writes */
 
        IMG_UINT32                      ui32NumDstSyncs;
-       PVRSRV_DEVICE_SYNC_OBJECT       asDstSyncs[SGX_MAX_DST_SYNCS];  
-       
+       PVRSRV_DEVICE_SYNC_OBJECT       asDstSyncs[SGX_MAX_DST_SYNCS_TQ];       
+       /* KEEP THESE 4 VARIABLES TOGETHER FOR UKERNEL BLOCK LOAD */
        IMG_UINT32              ui32TASyncWriteOpsPendingVal;
        IMG_DEV_VIRTADDR        sTASyncWriteOpsCompleteDevVAddr;
        IMG_UINT32              ui32TASyncReadOpsPendingVal;
        IMG_DEV_VIRTADDR        sTASyncReadOpsCompleteDevVAddr;
 
-       
+       /* KEEP THESE 4 VARIABLES TOGETHER FOR UKERNEL BLOCK LOAD */
        IMG_UINT32              ui323DSyncWriteOpsPendingVal;
        IMG_DEV_VIRTADDR        s3DSyncWriteOpsCompleteDevVAddr;
        IMG_UINT32              ui323DSyncReadOpsPendingVal;
@@ -194,68 +256,99 @@ typedef struct _SGXMKIF_TRANSFERCMD_SHARED_
 
 #if defined(SGX_FEATURE_2D_HARDWARE)
 typedef struct _SGXMKIF_2DCMD_SHARED_ {
-       
+       /* need to be able to check read and write ops on src, and update reads */
        IMG_UINT32                      ui32NumSrcSync;
        PVRSRV_DEVICE_SYNC_OBJECT       sSrcSyncData[SGX_MAX_2D_SRC_SYNC_OPS];
 
-       
+       /* need to be able to check reads and writes on dest, and update writes */
        PVRSRV_DEVICE_SYNC_OBJECT       sDstSyncData;
 
-       
+       /* need to be able to check reads and writes on TA ops, and update writes */
        PVRSRV_DEVICE_SYNC_OBJECT       sTASyncData;
 
-       
+       /* need to be able to check reads and writes on 2D ops, and update writes */
        PVRSRV_DEVICE_SYNC_OBJECT       s3DSyncData;
 } SGXMKIF_2DCMD_SHARED, *PSGXMKIF_2DCMD_SHARED;
-#endif 
+#endif /* SGX_FEATURE_2D_HARDWARE */
 
 
 typedef struct _SGXMKIF_HWDEVICE_SYNC_LIST_
 {
        IMG_DEV_VIRTADDR        sAccessDevAddr;
        IMG_UINT32                      ui32NumSyncObjects;
-       
+       /* Must be the last variable in the structure */
        PVRSRV_DEVICE_SYNC_OBJECT       asSyncData[1];
 } SGXMKIF_HWDEVICE_SYNC_LIST, *PSGXMKIF_HWDEVICE_SYNC_LIST;
 
 
-#define PVRSRV_USSE_EDM_INIT_COMPLETE                  (1UL << 0)      
-
-#define PVRSRV_USSE_EDM_POWMAN_IDLE_COMPLETE                           (1UL << 2)      
-#define PVRSRV_USSE_EDM_POWMAN_POWEROFF_COMPLETE                       (1UL << 3)      
-#define PVRSRV_USSE_EDM_POWMAN_POWEROFF_RESTART_IMMEDIATE      (1UL << 4)      
-#define PVRSRV_USSE_EDM_POWMAN_NO_WORK                                         (1UL << 5)      
-
-#define PVRSRV_USSE_EDM_INTERRUPT_HWR                  (1UL << 0)      
-#define PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER (1UL << 1)      
-
-#define PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE    (1UL << 0)      
+/*!
+ *****************************************************************************
+ * Microkernel initialisation status
+ *****************************************************************************/
+#define PVRSRV_USSE_EDM_INIT_COMPLETE                  (1UL << 0)      /*!< ukernel initialisation complete */
+
+/*!
+ *****************************************************************************
+ * Microkernel power status definitions
+ *****************************************************************************/
+#define PVRSRV_USSE_EDM_POWMAN_IDLE_COMPLETE                           (1UL << 2)      /*!< Signal from ukernel->Host indicating SGX is idle */
+#define PVRSRV_USSE_EDM_POWMAN_POWEROFF_COMPLETE                       (1UL << 3)      /*!< Signal from ukernel->Host indicating SGX can be powered down */
+#define PVRSRV_USSE_EDM_POWMAN_POWEROFF_RESTART_IMMEDIATE      (1UL << 4)      /*!< Signal from ukernel->Host indicating there is work to do immediately */
+#define PVRSRV_USSE_EDM_POWMAN_NO_WORK                                         (1UL << 5)      /*!< Signal from ukernel->Host indicating no work to do */
+
+/*!
+ *****************************************************************************
+ * EDM interrupt defines
+ *****************************************************************************/
+#define PVRSRV_USSE_EDM_INTERRUPT_HWR                  (1UL << 0)      /*!< EDM requesting hardware recovery */
+#define PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER (1UL << 1)      /*!< EDM requesting to be powered down */
+#define PVRSRV_USSE_EDM_INTERRUPT_IDLE                 (1UL << 2)      /*!< EDM indicating SGX idle */
+
+/*!
+ *****************************************************************************
+ * EDM Resource management defines
+ *****************************************************************************/
+#define PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE    (1UL << 0)      /*!< Signal from EDM->Host indicating clean-up request completion */
+#define PVRSRV_USSE_EDM_CLEANUPCMD_BUSY                        (1UL << 1)      /*!< Signal from EDM->Host indicating clean-up is blocked as the resource is busy */
+#define PVRSRV_USSE_EDM_CLEANUPCMD_DONE                        (1UL << 2)      /*!< Signal from EDM->Host indicating clean-up has been done */
 
 #if defined(FIX_HW_BRN_28889)
-#define PVRSRV_USSE_EDM_BIF_INVAL_COMPLETE             (1UL << 0)      
+/*!
+ *****************************************************************************
+ * EDM BIF Cache Invalidate defines
+ *****************************************************************************/
+#define PVRSRV_USSE_EDM_BIF_INVAL_COMPLETE             (1UL << 0)      /*!< Signal from EDM->Host indicating the BIF invalidate has started */
 #endif
 
+/*!
+ ****************************************************************************
+ * EDM / uKernel Get misc info defines
+ ****************************************************************************
+ */
 #define PVRSRV_USSE_MISCINFO_READY             0x1UL
-#define PVRSRV_USSE_MISCINFO_GET_STRUCT_SIZES  0x2UL   
+#define PVRSRV_USSE_MISCINFO_GET_STRUCT_SIZES  0x2UL   /*!< If set, getmiscinfo ukernel func returns structure sizes */
 #if defined(SUPPORT_SGX_EDM_MEMORY_DEBUG)
-#define PVRSRV_USSE_MISCINFO_MEMREAD                   0x4UL   
-#define PVRSRV_USSE_MISCINFO_MEMWRITE                  0x8UL   
+#define PVRSRV_USSE_MISCINFO_MEMREAD                   0x4UL   /*!< If set, getmiscinfo ukernel func reads arbitrary device mem */
+#define PVRSRV_USSE_MISCINFO_MEMWRITE                  0x8UL   /*!< If set, getmiscinfo ukernel func writes arbitrary device mem */
 #if !defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS)
-#define PVRSRV_USSE_MISCINFO_MEMREAD_FAIL              0x1UL << 31     
+#define PVRSRV_USSE_MISCINFO_MEMREAD_FAIL              0x1UL << 31     /* If set, ukernel was unable to read from the mem context */
 #endif
 #endif
 
 
+/* Cleanup command control word */
 #define        PVRSRV_CLEANUPCMD_RT            0x1U
 #define        PVRSRV_CLEANUPCMD_RC            0x2U
 #define        PVRSRV_CLEANUPCMD_TC            0x3U
 #define        PVRSRV_CLEANUPCMD_2DC           0x4U
 #define        PVRSRV_CLEANUPCMD_PB            0x5U
 
+/* Power command control word */
 #define PVRSRV_POWERCMD_POWEROFF       0x1U
 #define PVRSRV_POWERCMD_IDLE           0x2U
 #define PVRSRV_POWERCMD_RESUME         0x3U
 
+/* Context suspend command control word */
 #define PVRSRV_CTXSUSPCMD_SUSPEND      0x1U
 #define PVRSRV_CTXSUSPCMD_RESUME       0x2U
 
@@ -266,12 +359,20 @@ typedef struct _SGXMKIF_HWDEVICE_SYNC_LIST_
 #define SGX_BIF_DIR_LIST_INDEX_EDM     (0)
 #endif
 
+/*!
+ ******************************************************************************
+ * microkernel cache control requests
+ ******************************************************************************/
 #define        SGXMKIF_CC_INVAL_BIF_PT 0x1
 #define        SGXMKIF_CC_INVAL_BIF_PD 0x2
 #define SGXMKIF_CC_INVAL_BIF_SL        0x4
 #define SGXMKIF_CC_INVAL_DATA  0x8
 
 
+/*!
+ ******************************************************************************
+ * SGX microkernel interface structure sizes
+ ******************************************************************************/
 typedef struct _SGX_MISCINFO_STRUCT_SIZES_
 {
 #if defined (SGX_FEATURE_2D_HARDWARE)
@@ -295,30 +396,48 @@ typedef struct _SGX_MISCINFO_STRUCT_SIZES_
 
 
 #if defined(SUPPORT_SGX_EDM_MEMORY_DEBUG)
+/*!
+ *****************************************************************************
+ * SGX misc info for accessing device memory from ukernel
+ *****************************************************************************
+ */
 typedef struct _PVRSRV_SGX_MISCINFO_MEMACCESS
 {
-       IMG_DEV_VIRTADDR        sDevVAddr;              
-       IMG_DEV_PHYADDR         sPDDevPAddr;    
+       IMG_DEV_VIRTADDR        sDevVAddr;              /*!< dev virtual addr for mem access */
+       IMG_DEV_PHYADDR         sPDDevPAddr;    /*!< device physical addr of PD for the mem heap */
 } PVRSRV_SGX_MISCINFO_MEMACCESS;
 #endif
 
+/*!
+ *****************************************************************************
+ * SGX Misc Info structure used in the microkernel
+ * PVRSRV_SGX_MISCINFO_FEATURES is defined in sgxapi_km.h
+ ****************************************************************************/
 typedef struct _PVRSRV_SGX_MISCINFO_INFO
 {
        IMG_UINT32                                              ui32MiscInfoFlags;
-       PVRSRV_SGX_MISCINFO_FEATURES    sSGXFeatures;           
-       SGX_MISCINFO_STRUCT_SIZES               sSGXStructSizes;        
+       PVRSRV_SGX_MISCINFO_FEATURES    sSGXFeatures;           /*!< external info for client */
+       SGX_MISCINFO_STRUCT_SIZES               sSGXStructSizes;        /*!< internal info: microkernel structure sizes */
 #if defined(SUPPORT_SGX_EDM_MEMORY_DEBUG)
-       PVRSRV_SGX_MISCINFO_MEMACCESS   sSGXMemAccessSrc;       
-       PVRSRV_SGX_MISCINFO_MEMACCESS   sSGXMemAccessDest;      
+       PVRSRV_SGX_MISCINFO_MEMACCESS   sSGXMemAccessSrc;       /*!< internal info: for reading dev memory */
+       PVRSRV_SGX_MISCINFO_MEMACCESS   sSGXMemAccessDest;      /*!< internal info: for writing dev memory */
 #endif
 } PVRSRV_SGX_MISCINFO_INFO;
 
 #ifdef PVRSRV_USSE_EDM_STATUS_DEBUG
+/*!
+ *****************************************************************************
+ * Number of entries in the microkernel status buffer
+ *****************************************************************************/
 #define SGXMK_TRACE_BUFFER_SIZE 512
-#endif 
+#endif /* PVRSRV_USSE_EDM_STATUS_DEBUG */
 
-#define SGXMKIF_HWPERF_CB_SIZE                                 0x100   
+#define SGXMKIF_HWPERF_CB_SIZE                                 0x100   /* must be 2^n*/
 
+/*!
+ *****************************************************************************
+ * One entry in the HWPerf Circular Buffer.
+ *****************************************************************************/
 typedef struct _SGXMKIF_HWPERF_CB_ENTRY_
 {
        IMG_UINT32      ui32FrameNo;
@@ -329,11 +448,15 @@ typedef struct _SGXMKIF_HWPERF_CB_ENTRY_
        IMG_UINT32      ui32Info;
        IMG_UINT32      ui32TimeWraps;
        IMG_UINT32      ui32Time;
-       
+       /* NOTE: There should always be at least as many 3D cores as TA cores. */
        IMG_UINT32      ui32Counters[SGX_FEATURE_MP_CORE_COUNT_3D][PVRSRV_SGX_HWPERF_NUM_COUNTERS];
        IMG_UINT32      ui32MiscCounters[SGX_FEATURE_MP_CORE_COUNT_3D][PVRSRV_SGX_HWPERF_NUM_MISC_COUNTERS];
 } SGXMKIF_HWPERF_CB_ENTRY;
 
+/*!
+ *****************************************************************************
+ * The HWPerf Circular Buffer.
+ *****************************************************************************/
 typedef struct _SGXMKIF_HWPERF_CB_
 {
        IMG_UINT32                              ui32Woff;
@@ -343,5 +466,10 @@ typedef struct _SGXMKIF_HWPERF_CB_
 } SGXMKIF_HWPERF_CB;
 
 
-#endif 
+#endif /*  __SGX_MKIF_KM_H__ */
+
+/******************************************************************************
+ End of file (sgx_mkif_km.h)
+******************************************************************************/
+
 
diff --git a/services4/include/sgx_ukernel_status_codes.h b/services4/include/sgx_ukernel_status_codes.h
new file mode 100644 (file)
index 0000000..dc8f2f3
--- /dev/null
@@ -0,0 +1,966 @@
+/*************************************************************************/ /*!
+@File           sgx_ukernel_status_codes.h
+@Title          SGX microkernel debug status codes
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    SGX microkernel debug status codes
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+#ifndef __SGX_UKERNEL_STATUS_CODES_H__
+#define __SGX_UKERNEL_STATUS_CODES_H__
+
+/*
+       NOTE: Do not add any conditional macros to this file! There must be
+       no use of #if defined(). This file is included in srvkm to print
+       stringified ukernel status codes, it must build identically to
+       srvinit.
+*/
+
+/*
+       Users of this header might define this macro to do something
+       clever; the primary use right now is to generate a switch/case
+       LUT for debugging in srvkm. If you add a new code, make sure it
+       has a corresponding MKTC_ST.
+*/
+#ifndef MKTC_ST
+#define MKTC_ST(x)
+#endif
+
+/*
+       It would be nice to put these definitions into an enumeration, but USEASM
+       only has access to the C preprocessor so macros are required.
+*/
+
+/*
+       Bits 24-31 of these codes (0xAD) are a magic number used to help
+       distinguish between them and other debug information which can be
+       optionally dumped into the status buffer, e.g. sync object values.
+*/
+
+/*
+       Microkernel trace codes
+*/
+#define MKTC_EHEVENT_3DMEMFREE                                 0xAD000001
+MKTC_ST(MKTC_EHEVENT_3DMEMFREE)
+#define MKTC_EHEVENT_PIXELENDRENDER                            0xAD000002
+MKTC_ST(MKTC_EHEVENT_PIXELENDRENDER)
+#define MKTC_EHEVENT_ISPBREAKPOINT                             0xAD000004
+MKTC_ST(MKTC_EHEVENT_ISPBREAKPOINT)
+#define MKTC_EHEVENT_TAFINISHED                                        0xAD000005
+MKTC_ST(MKTC_EHEVENT_TAFINISHED)
+#define MKTC_EHEVENT_OUTOFMEM                                  0xAD000007
+MKTC_ST(MKTC_EHEVENT_OUTOFMEM)
+#define MKTC_EHEVENT_TATERMINATE                               0xAD000008
+MKTC_ST(MKTC_EHEVENT_TATERMINATE)
+#define MKTC_EHEVENT_TIMER                                             0xAD000009
+MKTC_ST(MKTC_EHEVENT_TIMER)
+#define MKTC_EHEVENT_SWEVENT                                   0xAD00000A
+MKTC_ST(MKTC_EHEVENT_SWEVENT)
+#define MKTC_EHEVENT_2DCOMPLETE                                        0xAD00000B
+MKTC_ST(MKTC_EHEVENT_2DCOMPLETE)
+
+#define MKTC_3DEVENT_3DMEMFREE                                 0xAD000100
+MKTC_ST(MKTC_3DEVENT_3DMEMFREE)
+#define MKTC_3DEVENT_PIXELENDRENDER                            0xAD000101
+MKTC_ST(MKTC_3DEVENT_PIXELENDRENDER)
+#define MKTC_3DEVENT_ISPBREAKPOINT                             0xAD000102
+MKTC_ST(MKTC_3DEVENT_ISPBREAKPOINT)
+#define MKTC_3DEVENT_END                                               0xAD000104
+MKTC_ST(MKTC_3DEVENT_END)
+#define MKTC_3DLB_3DMEMFREE                                            0xAD000180
+MKTC_ST(MKTC_3DLB_3DMEMFREE)
+#define MKTC_3DLB_PIXELENDRENDER                               0xAD000181
+MKTC_ST(MKTC_3DLB_PIXELENDRENDER)
+#define MKTC_3DLB_ISPBREAKPOINT                                        0xAD000182
+MKTC_ST(MKTC_3DLB_ISPBREAKPOINT)
+#define MKTC_3DLB_FIND3D                                               0xAD000183
+MKTC_ST(MKTC_3DLB_FIND3D)
+#define MKTC_3DLB_END                                                  0xAD000184
+MKTC_ST(MKTC_3DLB_END)
+
+#define MKTC_TAEVENT_TAFINISHED                                        0xAD000200
+MKTC_ST(MKTC_TAEVENT_TAFINISHED)
+#define MKTC_TAEVENT_END                                               0xAD000202
+MKTC_ST(MKTC_TAEVENT_END)
+#define MKTC_TALB_TAFINISHED                                   0xAD000280
+MKTC_ST(MKTC_TALB_TAFINISHED)
+#define MKTC_TALB_FINDTA                                               0xAD000281
+MKTC_ST(MKTC_TALB_FINDTA)
+#define MKTC_TALB_END                                                  0xAD000282
+MKTC_ST(MKTC_TALB_END)
+
+#define MKTC_CRRL_WRITEOPSBLOCKED                              0xAD000300
+MKTC_ST(MKTC_CRRL_WRITEOPSBLOCKED)
+#define MKTC_CRRL_READOPSBLOCKED                               0xAD000301
+MKTC_ST(MKTC_CRRL_READOPSBLOCKED)
+#define MKTC_CRRL_FOUNDRENDER                                  0xAD000302
+MKTC_ST(MKTC_CRRL_FOUNDRENDER)
+#define MKTC_CRRL_NORENDER                                             0xAD000303
+MKTC_ST(MKTC_CRRL_NORENDER)
+#define MKTC_CRRL_TARC_DIFFERENT                               0xAD000304
+MKTC_ST(MKTC_CRRL_TARC_DIFFERENT)
+#define MKTC_CRRL_BLOCKEDRC                                            0xAD000309
+MKTC_ST(MKTC_CRRL_BLOCKEDRC)
+#define MKTC_CRRL_BLOCKEDRTDATA                                        0xAD00030A
+MKTC_ST(MKTC_CRRL_BLOCKEDRTDATA)
+#define MKTC_CRRL_CONTEXT_SUSPENDED                            0xAD00030B
+MKTC_ST(MKTC_CRRL_CONTEXT_SUSPENDED)
+#define MKTC_CRRL_TAWAITINGFORMEM                              0xAD00030C
+MKTC_ST(MKTC_CRRL_TAWAITINGFORMEM)
+#define MKTC_CRRL_TAOOMBUTPRIOINV                              0xAD00030D
+MKTC_ST(MKTC_CRRL_TAOOMBUTPRIOINV)
+#define MKTC_CRRL_READOPS2BLOCKED                              0xAD00030E
+MKTC_ST(MKTC_CRRL_READOPS2BLOCKED)
+#define MKTC_CRRL_SRC_WRITEOPSBLOCKED                  0xAD00030F
+MKTC_ST(MKTC_CRRL_SRC_WRITEOPSBLOCKED)
+#define MKTC_CRRL_SRC_READOPSBLOCKED                   0xAD000310
+MKTC_ST(MKTC_CRRL_SRC_READOPSBLOCKED)
+#define MKTC_CRRL_TQ_WRITEOPSBLOCKED                   0xAD000311
+MKTC_ST(MKTC_CRRL_TQ_WRITEOPSBLOCKED)
+#define MKTC_CRRL_TQ_READOPSBLOCKED                            0xAD000312
+MKTC_ST(MKTC_CRRL_TQ_READOPSBLOCKED)
+
+#define MKTC_KICKRENDER_START                                  0xAD000400
+MKTC_ST(MKTC_KICKRENDER_START)
+#define MKTC_KICKRENDER_OVERLAP                                        0xAD000401
+MKTC_ST(MKTC_KICKRENDER_OVERLAP)
+#define MKTC_KICKRENDER_ISP_START                              0xAD000402
+MKTC_ST(MKTC_KICKRENDER_ISP_START)
+#define MKTC_KICKRENDER_RESUME                                 0xAD000403
+MKTC_ST(MKTC_KICKRENDER_RESUME)
+#define MKTC_KICKRENDER_CONFIG_REGION_HDRS             0xAD000404
+MKTC_ST(MKTC_KICKRENDER_CONFIG_REGION_HDRS)
+#define MKTC_KICKRENDER_END                                            0xAD000408
+MKTC_ST(MKTC_KICKRENDER_END)
+#define MKTC_KICKRENDER_RENDERCONTEXT                  0xAD000409
+MKTC_ST(MKTC_KICKRENDER_RENDERCONTEXT)
+#define MKTC_KICKRENDER_RTDATA                                 0xAD00040A
+MKTC_ST(MKTC_KICKRENDER_RTDATA)
+#define MKTC_KICKRENDER_PID                                            0xAD00040B
+MKTC_ST(MKTC_KICKRENDER_PID)
+
+#define MKTC_RENDERFINISHED_START                              0xAD000500
+MKTC_ST(MKTC_RENDERFINISHED_START)
+#define MKTC_RF_START_NEXT_MT                                  0xAD000501
+MKTC_ST(MKTC_RF_START_NEXT_MT)
+#define MKTC_RF_ALL_MTS_DONE                                   0xAD000502
+MKTC_ST(MKTC_RF_ALL_MTS_DONE)
+#define MKTC_RENDERFINISHED_END                                        0xAD000503
+MKTC_ST(MKTC_RENDERFINISHED_END)
+#define MKTC_VISQUERY_START                                            0xAD000504
+MKTC_ST(MKTC_VISQUERY_START)
+#define MKTC_VISQUERY_END                                              0xAD000505
+MKTC_ST(MKTC_VISQUERY_END)
+#define MKTC_TRANSFERRENDERFINISHED_START              0xAD000508
+MKTC_ST(MKTC_TRANSFERRENDERFINISHED_START)
+#define MKTC_TRANSFERRENDERFINISHED_END                        0xAD000509
+MKTC_ST(MKTC_TRANSFERRENDERFINISHED_END)
+#define MKTC_TRF_UPDATESTATUSVALS                              0xAD00050A
+MKTC_ST(MKTC_TRF_UPDATESTATUSVALS)
+#define MKTC_TRF_UPDATESTATUSVALS_DONE                 0xAD00050B
+MKTC_ST(MKTC_TRF_UPDATESTATUSVALS_DONE)
+
+#define MKTC_PIXELENDRENDER_START                              0xAD000600
+MKTC_ST(MKTC_PIXELENDRENDER_START)
+#define MKTC_PIXELENDRENDER_AFTERLOCK                  0xAD000601
+MKTC_ST(MKTC_PIXELENDRENDER_AFTERLOCK)
+#define MKTC_PIXELENDRENDER_END                                        0xAD000602
+MKTC_ST(MKTC_PIXELENDRENDER_END)
+#define MKTC_PIXELENDRENDER_TLQEND                             0xAD000603
+MKTC_ST(MKTC_PIXELENDRENDER_TLQEND)
+
+#define MKTC_3DMEMFREE_START                                   0xAD000700
+MKTC_ST(MKTC_3DMEMFREE_START)
+#define MKTC_3DMEMFREE_AFTERLOCK                               0xAD000701
+MKTC_ST(MKTC_3DMEMFREE_AFTERLOCK)
+#define MKTC_3DMEMFREE_TESTEOR                                 0xAD000702
+MKTC_ST(MKTC_3DMEMFREE_TESTEOR)
+#define MKTC_3DMEMFREE_END                                             0xAD000703
+MKTC_ST(MKTC_3DMEMFREE_END)
+
+#define MKTC_KICKTA_START                                              0xAD000800
+MKTC_ST(MKTC_KICKTA_START)
+#define MKTC_KICKTA_OVERLAP                                            0xAD000801
+MKTC_ST(MKTC_KICKTA_OVERLAP)
+#define MKTC_KICKTA_RESETCONTEXT                               0xAD000802
+MKTC_ST(MKTC_KICKTA_RESETCONTEXT)
+#define MKTC_KICKTA_VDM_START                                  0xAD000803
+MKTC_ST(MKTC_KICKTA_VDM_START)
+#define MKTC_KICKTA_END                                                        0xAD000804
+MKTC_ST(MKTC_KICKTA_END)
+#define MKTC_KICKTA_RENDERCONTEXT                              0xAD000805
+MKTC_ST(MKTC_KICKTA_RENDERCONTEXT)
+#define MKTC_KICKTA_RTDATA                                             0xAD000806
+MKTC_ST(MKTC_KICKTA_RTDATA)
+#define MKTC_KICKTA_RESET_VDMCSSTATUS                  0xAD000807
+MKTC_ST(MKTC_KICKTA_RESET_VDMCSSTATUS)
+#define MKTC_KICKTA_RESET_BUFFERS                              0xAD000808
+MKTC_ST(MKTC_KICKTA_RESET_BUFFERS)
+#define MKTC_KICKTA_PID                                                        0xAD000809
+MKTC_ST(MKTC_KICKTA_PID)
+#define MKTC_KICKTA_TACMD_DEBUG                                        0xAD00080A
+MKTC_ST(MKTC_KICKTA_TACMD_DEBUG)
+#define MKTC_KICKTA_FREECONTEXT                                        0xAD00080B
+MKTC_ST(MKTC_KICKTA_FREECONTEXT)
+#define MKTC_KICKTA_PIM_PATCHING                               0xAD00080C
+MKTC_ST(MKTC_KICKTA_PIM_PATCHING)
+
+#define MKTC_KICKTA_CHKPT_START_DUMMY_CS               0xAD0008A1
+MKTC_ST(MKTC_KICKTA_CHKPT_START_DUMMY_CS)
+#define MKTC_KICKTA_CHKPT_START_DUMMY_TAK              0xAD0008A2
+MKTC_ST(MKTC_KICKTA_CHKPT_START_DUMMY_TAK)
+#define MKTC_KICKTA_CHKPT_WAIT_FOR_DUMMY_KICK  0xAD0008A3
+MKTC_ST(MKTC_KICKTA_CHKPT_WAIT_FOR_DUMMY_KICK)
+#define MKTC_KICKTA_CHKPT_WAIT_NEXT_CORE               0xAD0008A4
+MKTC_ST(MKTC_KICKTA_CHKPT_WAIT_NEXT_CORE)
+#define MKTC_KICKTA_CHKPT_RESET_COMPLETE               0xAD0008A5
+MKTC_ST(MKTC_KICKTA_CHKPT_RESET_COMPLETE)
+#define MKTC_KICKTA_CHKPT_CHECK_SWITCH                 0xAD0008A6
+MKTC_ST(MKTC_KICKTA_CHKPT_CHECK_SWITCH)
+
+#define MKTC_HOSTKICK_START                                            0xAD000900
+MKTC_ST(MKTC_HOSTKICK_START)
+#define MKTC_HOSTKICK_END                                              0xAD000901
+MKTC_ST(MKTC_HOSTKICK_END)
+#define MKTC_HOSTKICK_PROCESS_QUEUES_END               0xAD000902
+MKTC_ST(MKTC_HOSTKICK_PROCESS_QUEUES_END)
+#define MKTC_HOSTKICK_2D                                               0xAD000903
+MKTC_ST(MKTC_HOSTKICK_2D)
+#define MKTC_HOSTKICK_TRANSFER                                 0xAD000904
+MKTC_ST(MKTC_HOSTKICK_TRANSFER)
+#define MKTC_HOSTKICK_TA                                               0xAD000905
+MKTC_ST(MKTC_HOSTKICK_TA)
+#define MKTC_HOSTKICK_PROCESS_QUEUES                   0xAD000906
+MKTC_ST(MKTC_HOSTKICK_PROCESS_QUEUES)
+#define MKTC_HOSTKICK_RESUME                                   0xAD000908
+MKTC_ST(MKTC_HOSTKICK_RESUME)
+#define MKTC_HOSTKICK_POWEROFF                                 0xAD000909
+MKTC_ST(MKTC_HOSTKICK_POWEROFF)
+#define MKTC_HOSTKICK_IDLE                                             0xAD00090A
+MKTC_ST(MKTC_HOSTKICK_IDLE)
+#define MKTC_HOSTKICK_CTXSUSPEND                               0xAD00090B
+MKTC_ST(MKTC_HOSTKICK_CTXSUSPEND)
+#define MKTC_HOSTKICK_CTXRESUME                                        0xAD00090C
+MKTC_ST(MKTC_HOSTKICK_CTXRESUME)
+
+#define MKTC_TIMER_POTENTIAL_TA_LOCKUP                 0xAD000A00
+MKTC_ST(MKTC_TIMER_POTENTIAL_TA_LOCKUP)
+#define MKTC_TIMER_POTENTIAL_3D_LOCKUP                 0xAD000A01
+MKTC_ST(MKTC_TIMER_POTENTIAL_3D_LOCKUP)
+#define MKTC_TIMER_CTAL_START                                  0xAD000A02
+MKTC_ST(MKTC_TIMER_CTAL_START)
+#define MKTC_TIMER_CTAL_END                                            0xAD000A03
+MKTC_ST(MKTC_TIMER_CTAL_END)
+#define MKTC_TIMER_C3DL_START                                  0xAD000A04
+MKTC_ST(MKTC_TIMER_C3DL_START)
+#define MKTC_TIMER_C3DL_END                                            0xAD000A05
+MKTC_ST(MKTC_TIMER_C3DL_END)
+#define MKTC_TIMER_LOCKUP                                              0xAD000A0A
+MKTC_ST(MKTC_TIMER_LOCKUP)
+#define MKTC_TIMER_NOT_TA_LOCKUP                               0xAD000A0B
+MKTC_ST(MKTC_TIMER_NOT_TA_LOCKUP)
+#define MKTC_TIMER_NOT_3D_LOCKUP                               0xAD000A0C
+MKTC_ST(MKTC_TIMER_NOT_3D_LOCKUP)
+#define MKTC_TIMER_2D_LOCKUP                                   0xAD000A0D
+MKTC_ST(MKTC_TIMER_2D_LOCKUP)
+#define MKTC_TIMER_POTENTIAL_2D_LOCKUP                 0xAD000A10
+MKTC_ST(MKTC_TIMER_POTENTIAL_2D_LOCKUP)
+#define MKTC_TIMER_C2DL_START                                  0xAD000A11
+MKTC_ST(MKTC_TIMER_C2DL_START)
+#define MKTC_TIMER_C2DL_END                                            0xAD000A12
+MKTC_ST(MKTC_TIMER_C2DL_END)
+#define MKTC_TIMER_NOT_2D_LOCKUP                               0xAD000A13
+MKTC_ST(MKTC_TIMER_NOT_2D_LOCKUP)
+#define MKTC_TIMER_ABORTALL                                            0xAD000A0E
+MKTC_ST(MKTC_TIMER_ABORTALL)
+#define MKTC_TIMER_END                                                 0xAD000A0F
+MKTC_ST(MKTC_TIMER_END)
+
+#define MKTC_HWR_START                                                 0xAD000B00
+MKTC_ST(MKTC_HWR_START)
+#define MKTC_HWR_END                                                   0xAD000B01
+MKTC_ST(MKTC_HWR_END)
+#define MKTC_HWR_HKS                                                   0xAD000B02
+MKTC_ST(MKTC_HWR_HKS)
+#define MKTC_HWR_PRL                                                   0xAD000B03
+MKTC_ST(MKTC_HWR_PRL)
+#define MKTC_HWR_PRL_DP                                                        0xAD000B04
+MKTC_ST(MKTC_HWR_PRL_DP)
+#define MKTC_HWR_CRL                                                   0xAD000B05
+MKTC_ST(MKTC_HWR_CRL)
+#define MKTC_HWR_CRL_DP                                                        0xAD000B06
+MKTC_ST(MKTC_HWR_CRL_DP)
+#define MKTC_HWR_TRL                                                   0xAD000B07
+MKTC_ST(MKTC_HWR_TRL)
+#define MKTC_HWR_TRL_DP                                                        0xAD000B08
+MKTC_ST(MKTC_HWR_TRL_DP)
+#define MKTC_HWR_ISC                                                   0xAD000B09
+MKTC_ST(MKTC_HWR_ISC)
+#define MKTC_HWR_2DL                                                   0xAD000B0A
+MKTC_ST(MKTC_HWR_2DL)
+#define MKTC_HWR_CLEANUP                                               0xAD000B0B
+MKTC_ST(MKTC_HWR_CLEANUP)
+
+#define MKTC_URSV_START                                                        0xAD000C00
+MKTC_ST(MKTC_URSV_START)
+#define MKTC_URSV_UPDATEWRITEOPS                               0xAD000C01
+MKTC_ST(MKTC_URSV_UPDATEWRITEOPS)
+#define MKTC_URSV_UPDATESTATUSVALS                             0xAD000C03
+MKTC_ST(MKTC_URSV_UPDATESTATUSVALS)
+#define MKTC_URSV_UPDATESTATUSVALS_DONE                        0xAD000C04
+MKTC_ST(MKTC_URSV_UPDATESTATUSVALS_DONE)
+#define MKTC_URSV_END                                                  0xAD000C05
+MKTC_ST(MKTC_URSV_END)
+
+#define MKTC_STORETACONTEXT_START                              0xAD000D00
+MKTC_ST(MKTC_STORETACONTEXT_START)
+#define MKTC_STORETACONTEXT_END                                        0xAD000D01
+MKTC_ST(MKTC_STORETACONTEXT_END)
+#define MKTC_LOADTACONTEXT_START                               0xAD000D02
+MKTC_ST(MKTC_LOADTACONTEXT_START)
+#define MKTC_LOADTACONTEXT_END                                 0xAD000D03
+MKTC_ST(MKTC_LOADTACONTEXT_END)
+#define MKTC_STORE3DCONTEXT_START                              0xAD000D04
+MKTC_ST(MKTC_STORE3DCONTEXT_START)
+#define MKTC_STORE3DCONTEXT_END                                        0xAD000D05
+MKTC_ST(MKTC_STORE3DCONTEXT_END)
+#define MKTC_LOAD3DCONTEXT_START                               0xAD000D06
+MKTC_ST(MKTC_LOAD3DCONTEXT_START)
+#define MKTC_LOAD3DCONTEXT_END                                 0xAD000D07
+MKTC_ST(MKTC_LOAD3DCONTEXT_END)
+
+#define MKTC_FINDTA_POWERREQUEST                               0xAD000E00
+MKTC_ST(MKTC_FINDTA_POWERREQUEST)
+#define MKTC_FINDTA_TA3D_OVERLAP_BLOCKED               0xAD000E01
+MKTC_ST(MKTC_FINDTA_TA3D_OVERLAP_BLOCKED)
+#define MKTC_FINDTA_RTDATA_RENDERING                   0xAD000E02
+MKTC_ST(MKTC_FINDTA_RTDATA_RENDERING)
+#define MKTC_FINDTA_3DRC_DIFFERENT                             0xAD000E03
+MKTC_ST(MKTC_FINDTA_3DRC_DIFFERENT)
+#define MKTC_FINDTA_WRITEOPSBLOCKED                            0xAD000E04
+MKTC_ST(MKTC_FINDTA_WRITEOPSBLOCKED)
+#define MKTC_FINDTA_READOPSBLOCKED                             0xAD000E05
+MKTC_ST(MKTC_FINDTA_READOPSBLOCKED)
+#define MKTC_FINDTA_RESIZE_PB                                  0xAD000E06
+MKTC_ST(MKTC_FINDTA_RESIZE_PB)
+#define MKTC_FINDTA_RESIZE_PB_BLOCKED                  0xAD000E07
+MKTC_ST(MKTC_FINDTA_RESIZE_PB_BLOCKED)
+#define MKTC_FINDTA_SHRINK_PB                                  0xAD000E08
+MKTC_ST(MKTC_FINDTA_SHRINK_PB)
+#define        MKTC_FINDTA_TAPB_DIFFERENT                              0xAD000E09
+MKTC_ST(MKTC_FINDTA_TAPB_DIFFERENT)
+#define        MKTC_FINDTA_TACONTEXT_DIFFERENT                 0xAD000E0A
+MKTC_ST(MKTC_FINDTA_TACONTEXT_DIFFERENT)
+#define MKTC_FINDTA_TA2D_OVERLAP_BLOCKED               0xAD000E0B
+MKTC_ST(MKTC_FINDTA_TA2D_OVERLAP_BLOCKED)
+#define MKTC_FINDTA_CONTEXT_SUSPENDED                  0xAD000E0C
+MKTC_ST(MKTC_FINDTA_CONTEXT_SUSPENDED)
+#define MKTC_FINDTA_SRC_READOPSBLOCKED                 0xAD000E0D
+MKTC_ST(MKTC_FINDTA_SRC_READOPSBLOCKED)
+#define MKTC_FINDTA_SRC_WRITEOPSBLOCKED                        0xAD000E0E
+MKTC_ST(MKTC_FINDTA_SRC_WRITEOPSBLOCKED)
+#define MKTC_FINDTA_READOPS2BLOCKED                            0xAD000E0F
+MKTC_ST(MKTC_FINDTA_READOPS2BLOCKED)
+
+#define MKTC_CTRL_SRCREADOPSBLOCKED                            0xAD000F00
+MKTC_ST(MKTC_CTRL_SRCREADOPSBLOCKED)
+#define MKTC_CTRL_SRCWRITEOPSBLOCKED                   0xAD000F01
+MKTC_ST(MKTC_CTRL_SRCWRITEOPSBLOCKED)
+#define MKTC_CTRL_DSTREADOPSBLOCKED                            0xAD000F02
+MKTC_ST(MKTC_CTRL_DSTREADOPSBLOCKED)
+#define MKTC_CTRL_DSTWRITEOPSBLOCKED                   0xAD000F03
+MKTC_ST(MKTC_CTRL_DSTWRITEOPSBLOCKED)
+#define MKTC_CTRL_TARC_DIFFERENT                               0xAD000F04
+MKTC_ST(MKTC_CTRL_TARC_DIFFERENT)
+#define MKTC_CTRL_CONTEXT_SUSPENDED                            0xAD000F05
+MKTC_ST(MKTC_CTRL_CONTEXT_SUSPENDED)
+#define MKTC_CTRL_SRCREADOPS2BLOCKED                   0xAD000F06
+MKTC_ST(MKTC_CTRL_SRCREADOPS2BLOCKED)
+#define MKTC_CTRL_3D_WRITEOPSBLOCKED                   0xAD000F07
+MKTC_ST(MKTC_CTRL_3D_WRITEOPSBLOCKED)
+#define MKTC_CTRL_3D_READOPSBLOCKED                            0xAD000F08
+MKTC_ST(MKTC_CTRL_3D_READOPSBLOCKED)
+
+#define MKTC_DPTA_START                                                        0xAD001000
+MKTC_ST(MKTC_DPTA_START)
+#define MKTC_DPTA_UPDATESTATUSVALS                             0xAD001001
+MKTC_ST(MKTC_DPTA_UPDATESTATUSVALS)
+#define MKTC_DPTA_UPDATESTATUSVALS_DONE                        0xAD001002
+MKTC_ST(MKTC_DPTA_UPDATESTATUSVALS_DONE)
+#define MKTC_DPTA_NORENDER                                             0xAD001003
+MKTC_ST(MKTC_DPTA_NORENDER)
+#define MKTC_DPTA_MEMFREE                                              0xAD001004
+MKTC_ST(MKTC_DPTA_MEMFREE)
+#define MKTC_DPTA_INC_COMPLETECOUNT                            0xAD001005
+MKTC_ST(MKTC_DPTA_INC_COMPLETECOUNT)
+
+#define MKTC_INVALDC                                                   0xAD001100
+MKTC_ST(MKTC_INVALDC)
+#define MKTC_INVALPT                                                   0xAD001101
+MKTC_ST(MKTC_INVALPT)
+#define MKTC_INVALSLC                                                  0xAD001102
+MKTC_ST(MKTC_INVALSLC)
+#define MKTC_INVALDATA                                                 0xAD001103
+MKTC_ST(MKTC_INVALDATA)
+
+#define MKTC_RESTARTTA                                                 0xAD001200
+MKTC_ST(MKTC_RESTARTTA)
+#define MKTC_CSABORTNONGBL                                             0xAD001201
+MKTC_ST(MKTC_CSABORTNONGBL)
+#define MKTC_CSABORTALL                                                        0xAD001202
+MKTC_ST(MKTC_CSABORTALL)
+#define MKTC_CSRENDERINPROGRESS                                        0xAD001203
+MKTC_ST(MKTC_CSRENDERINPROGRESS)
+#define MKTC_TATERMRENDERINPROGRESS                            0xAD001204
+MKTC_ST(MKTC_TATERMRENDERINPROGRESS)
+#define MKTC_RESTARTTANORENDER                                 0xAD001205
+MKTC_ST(MKTC_RESTARTTANORENDER)
+#define MKTC_SPM_KICKRENDER                                            0xAD001206
+MKTC_ST(MKTC_SPM_KICKRENDER)
+#define MKTC_SPM_RESUME_ABORTCOMPLETE                  0xAD001208
+MKTC_ST(MKTC_SPM_RESUME_ABORTCOMPLETE)
+#define        MKTC_RESUMEVDM                                                  0xAD001209
+MKTC_ST(MKTC_RESUMEVDM)
+#define        MKTC_REMOVE_RESERVE_MEM                                 0xAD00120A
+MKTC_ST(MKTC_REMOVE_RESERVE_MEM)
+#define        MKTC_INCREASEZLSTHRESHOLD                               0xAD00120B
+MKTC_ST(MKTC_INCREASEZLSTHRESHOLD)
+#define MKTC_CSFORCEABORTALL                                   0xAD00120C
+MKTC_ST(MKTC_CSFORCEABORTALL)
+
+#define MKTC_DUMMY_DEPTH                                               0xAD00120D
+MKTC_ST(MKTC_DUMMY_DEPTH)
+#define MKTC_DUMMY_DEPTH_CS                                            0xAD00120E
+MKTC_ST(MKTC_DUMMY_DEPTH_CS)
+
+#define MKTC_MTETE_OOM                                                 0xAD00120F
+MKTC_ST(MKTC_MTETE_OOM)
+#define        MKTC_MTETE_OOM_FIRST_STORE_REF                  0xAD001210
+MKTC_ST(MKTC_MTETE_OOM_FIRST_STORE_REF)
+#define MKTC_MERGE_STATE_TABLES                                        0xAD001211
+MKTC_ST(MKTC_MERGE_STATE_TABLES)
+#define MKTC_NO_PAGES_LEFT_FOR_23055                   0xAD001212
+MKTC_ST(MKTC_NO_PAGES_LEFT_FOR_23055)
+#define MKTC_NO_STATE_MODS                                             0xAD001213
+MKTC_ST(MKTC_NO_STATE_MODS)
+#define MKTC_FIND_MTE_PAGE_IN_STATE                            0xAD001214
+MKTC_ST(MKTC_FIND_MTE_PAGE_IN_STATE)
+#define MKTC_MTE_PAGE_FOUND                                            0xAD001215
+MKTC_ST(MKTC_MTE_PAGE_FOUND)
+#define MKTC_MOVE_MTE_PAGE_TO_TA_STATE                 0xAD001216
+MKTC_ST(MKTC_MOVE_MTE_PAGE_TO_TA_STATE)
+#define MKTC_MOVE_MTE_PAGE_TO_TA_STATE_END             0xAD001217
+MKTC_ST(MKTC_MOVE_MTE_PAGE_TO_TA_STATE_END)
+#define MKTC_ZERO_ZLS_THRESHOLD                                        0xAD001218
+MKTC_ST(MKTC_ZERO_ZLS_THRESHOLD)
+#define MKTC_RESTORE_ZLS_THRESHOLD                             0xAD001219
+MKTC_ST(MKTC_RESTORE_ZLS_THRESHOLD)
+#define MKTC_FIND_MTE_PAGE_IN_CSM                              0xAD00121A
+MKTC_ST(MKTC_FIND_MTE_PAGE_IN_CSM)
+#define MKTC_REISSUE_MTE_PAGE                                  0xAD00121B
+MKTC_ST(MKTC_REISSUE_MTE_PAGE)
+#define MKTC_REISSUE_MTE_PAGE_REQUIRED                 0xAD00121C
+MKTC_ST(MKTC_REISSUE_MTE_PAGE_REQUIRED)
+#define MKTC_REISSUE_MTE_PAGE_END                              0xAD00121D
+MKTC_ST(MKTC_REISSUE_MTE_PAGE_END)
+#define MKTC_RESET_TE_PSG                                              0xAD00121E
+MKTC_ST(MKTC_RESET_TE_PSG)
+
+#define MKTC_OOM_WRITEOPSBLOCKED                               0xAD00121F
+MKTC_ST(MKTC_OOM_WRITEOPSBLOCKED)
+#define MKTC_OOM_READOPSBLOCKED                                        0xAD001220
+MKTC_ST(MKTC_OOM_READOPSBLOCKED)
+#define MKTC_OOM_SRC_WRITEOPSBLOCKED                   0xAD001221
+MKTC_ST(MKTC_OOM_SRC_WRITEOPSBLOCKED)
+#define MKTC_OOM_SRC_READOPSBLOCKED                            0xAD001222
+MKTC_ST(MKTC_OOM_SRC_READOPSBLOCKED)
+#define MKTC_OOM_SPM_DEADLOCK                                  0xAD001223
+MKTC_ST(MKTC_OOM_SPM_DEADLOCK)
+#define MKTC_OOM_SPM_DEADLOCK_MEM_ADDED                        0xAD001224
+MKTC_ST(MKTC_OOM_SPM_DEADLOCK_MEM_ADDED)
+#define MKTC_RESET                                                             0xAD001225
+MKTC_ST(MKTC_RESET)
+#define        MKTC_SPM_INVALID_ZLSCONFIG                              0xAD001226
+MKTC_ST(MKTC_SPM_INVALID_ZLSCONFIG)
+
+#define MKTC_OOM_TYPE_MT                                               0xAD00122A
+MKTC_ST(MKTC_OOM_TYPE_MT)
+#define MKTC_OOM_TYPE_GLOBAL                                   0xAD001230
+MKTC_ST(MKTC_OOM_TYPE_GLOBAL)
+#define MKTC_OOM_CAUSE_GBL_OOM                                 0xAD001231
+MKTC_ST(MKTC_OOM_CAUSE_GBL_OOM)
+#define MKTC_OOM_RESTORE_LIST_SIZE                             0xAD001232
+MKTC_ST(MKTC_OOM_RESTORE_LIST_SIZE)
+
+#define MKTC_CHECK_MTE_PAGE_REISSUE                            0xAD001240
+MKTC_ST(MKTC_CHECK_MTE_PAGE_REISSUE)
+#define MKTC_CPRI_VALID_ENTRIES                                        0xAD001241
+MKTC_ST(MKTC_CPRI_VALID_ENTRIES)
+#define MKTC_CPRI_STORE_DPLIST                                 0xAD001242
+MKTC_ST(MKTC_CPRI_STORE_DPLIST)
+#define MKTC_CPRI_STORE_OTPM_CSM                               0xAD001243
+MKTC_ST(MKTC_CPRI_STORE_OTPM_CSM)
+#define MKTC_CPRI_ABORT_MT_IDX                                 0xAD001244
+MKTC_ST(MKTC_CPRI_ABORT_MT_IDX)
+#define MKTC_CPRI_ABORT_CORE_IDX                               0xAD001245
+MKTC_ST(MKTC_CPRI_ABORT_CORE_IDX)
+#define MKTC_CPRI_CSM_TABLE_DATA                               0xAD001246
+MKTC_ST(MKTC_CPRI_CSM_TABLE_DATA)
+#define MKTC_CPRI_PIM_DATA                                             0xAD001247
+MKTC_ST(MKTC_CPRI_PIM_DATA)
+#define MKTC_CPRI_DO_CIRCULAR_TEST                             0xAD001248
+MKTC_ST(MKTC_CPRI_DO_CIRCULAR_TEST)
+#define MKTC_CPRI_WRITE_ENTRIES                                        0xAD001249
+MKTC_ST(MKTC_CPRI_WRITE_ENTRIES)
+
+#define        MKTC_MTE_ENTRY_NOT_IN_ANY_LIST                  0xAD001250
+MKTC_ST(MKTC_MTE_ENTRY_NOT_IN_ANY_LIST)
+
+#define        MKTC_SPMAC_IGNORE_TERMINATE                             0xAD001251
+MKTC_ST(MKTC_SPMAC_IGNORE_TERMINATE)
+
+#define MKTC_SPMAC_REQUEST_3D_TIMEOUT                  0xAD001252
+MKTC_ST(MKTC_SPMAC_REQUEST_3D_TIMEOUT)
+#define MKTC_SPMAC_3D_TIMEOUT_COMPLETE                 0xAD001253
+MKTC_ST(MKTC_SPMAC_3D_TIMEOUT_COMPLETE)
+#define MKTC_OOM_READOPS2BLOCKED                               0xAD001254
+MKTC_ST(MKTC_OOM_READOPS2BLOCKED)
+
+/* PB Load/store status */
+#define MKTC_LOADTAPB_START                                            0xAD001300
+MKTC_ST(MKTC_LOADTAPB_START)
+#define MKTC_LOADTAPB_END                                              0xAD001301
+MKTC_ST(MKTC_LOADTAPB_END)
+#define MKTC_STORETAPB_START                                   0xAD001302
+MKTC_ST(MKTC_STORETAPB_START)
+#define MKTC_STORETAPB_END                                             0xAD001303
+MKTC_ST(MKTC_STORETAPB_END)
+#define MKTC_LOAD3DPB_START                                            0xAD001304
+MKTC_ST(MKTC_LOAD3DPB_START)
+#define MKTC_LOAD3DPB_END                                              0xAD001305
+MKTC_ST(MKTC_LOAD3DPB_END)
+#define MKTC_STORE3DPB_START                                   0xAD001306
+MKTC_ST(MKTC_STORE3DPB_START)
+#define MKTC_STORE3DPB_END                                             0xAD001307
+MKTC_ST(MKTC_STORE3DPB_END)
+#define MKTC_LOADTAPB_PAGETABLE_DONE                   0xAD001308
+MKTC_ST(MKTC_LOADTAPB_PAGETABLE_DONE)
+#define MKTC_LOAD3DPB_PAGETABLE_DONE                   0xAD001309
+MKTC_ST(MKTC_LOAD3DPB_PAGETABLE_DONE)
+
+#define MKTC_TIMER_RC_CLEANUP                                  0xAD001400
+MKTC_ST(MKTC_TIMER_RC_CLEANUP)
+#define MKTC_TIMER_RC_CLEANUP_DONE                             0xAD001401
+MKTC_ST(MKTC_TIMER_RC_CLEANUP_DONE)
+#define MKTC_TIMER_RC_CLEANUP_BUSY                             0xAD001402
+MKTC_ST(MKTC_TIMER_RC_CLEANUP_BUSY)
+#define MKTC_TIMER_RT_CLEANUP                                  0xAD001410
+MKTC_ST(MKTC_TIMER_RT_CLEANUP)
+#define MKTC_TIMER_RT_CLEANUP_DONE                             0xAD001411
+MKTC_ST(MKTC_TIMER_RT_CLEANUP_DONE)
+#define MKTC_TIMER_RT_CLEANUP_PENDING                  0xAD001412
+MKTC_ST(MKTC_TIMER_RT_CLEANUP_PENDING)
+#define MKTC_TIMER_RT_CLEANUP_TIDYPARTIALLIST  0xAD001413
+MKTC_ST(MKTC_TIMER_RT_CLEANUP_TIDYPARTIALLIST)
+#define MKTC_TIMER_RT_CLEANUP_BUSY                             0xAD001414
+MKTC_ST(MKTC_TIMER_RT_CLEANUP_BUSY)
+#define MKTC_TIMER_TC_CLEANUP                                  0xAD001420
+MKTC_ST(MKTC_TIMER_TC_CLEANUP)
+#define MKTC_TIMER_TC_CLEANUP_DONE                             0xAD001421
+MKTC_ST(MKTC_TIMER_TC_CLEANUP_DONE)
+#define MKTC_TIMER_TC_CLEANUP_BUSY                             0xAD001422
+MKTC_ST(MKTC_TIMER_TC_CLEANUP_BUSY)
+#define MKTC_TIMER_2DC_CLEANUP                                 0xAD001430
+MKTC_ST(MKTC_TIMER_2DC_CLEANUP)
+#define MKTC_TIMER_2DC_CLEANUP_DONE                            0xAD001431
+MKTC_ST(MKTC_TIMER_2DC_CLEANUP_DONE)
+#define MKTC_TIMER_2DC_CLEANUP_BUSY                            0xAD001432
+MKTC_ST(MKTC_TIMER_2DC_CLEANUP_BUSY)
+#define MKTC_TIMER_SHAREDPBDESC_CLEANUP                        0xAD001440
+MKTC_ST(MKTC_TIMER_SHAREDPBDESC_CLEANUP)
+
+
+#define MKTC_TIMER_ISP_SWITCH_POTENTIAL_LOCKUP 0xAD001450
+MKTC_ST(MKTC_TIMER_ISP_SWITCH_POTENTIAL_LOCKUP)
+#define MKTC_TIMER_ISP_SWITCH_FORCE_SWITCH             0xAD001451
+MKTC_ST(MKTC_TIMER_ISP_SWITCH_FORCE_SWITCH)
+
+#define MKTC_UTSO_UPDATEREADOPS                                        0xAD001600
+MKTC_ST(MKTC_UTSO_UPDATEREADOPS)
+#define MKTC_UTSO_UPDATEWRITEOPS                               0xAD001601
+MKTC_ST(MKTC_UTSO_UPDATEWRITEOPS)
+
+#define MKTC_TAFINISHED_UPDATESTATUSVALS               0xAD001700
+MKTC_ST(MKTC_TAFINISHED_UPDATESTATUSVALS)
+#define MKTC_TAFINISHED_UPDATESTATUSVALS_DONE  0xAD001701
+MKTC_ST(MKTC_TAFINISHED_UPDATESTATUSVALS_DONE)
+#define MKTC_TAFINISHED_NORENDER                               0xAD001702
+MKTC_ST(MKTC_TAFINISHED_NORENDER)
+#define MKTC_TAFINISHED_LASTKICK                               0xAD001703
+MKTC_ST(MKTC_TAFINISHED_LASTKICK)
+#define MKTC_TAFINISHED_FINDRENDER                             0xAD001704
+MKTC_ST(MKTC_TAFINISHED_FINDRENDER)
+#define MKTC_TAFINISHED_FINDTA                                 0xAD001705
+MKTC_ST(MKTC_TAFINISHED_FINDTA)
+#define MKTC_TAFINISHED_END                                            0xAD001706
+MKTC_ST(MKTC_TAFINISHED_END)
+#define MKTC_TAF_SPM_DEADLOCK_MEM_REMOVED              0xAD001707
+MKTC_ST(MKTC_TAF_SPM_DEADLOCK_MEM_REMOVED)
+#define MKTC_TAF_RESERVE_MEM                                   0xAD001708
+MKTC_ST(MKTC_TAF_RESERVE_MEM)
+#define MKTC_TAF_RESERVE_MEM_REQUEST_RENDER            0xAD001709
+MKTC_ST(MKTC_TAF_RESERVE_MEM_REQUEST_RENDER)
+#define MKTC_TAF_RESERVE_FREE_RENDER_FINISHED  0xAD00170A
+MKTC_ST(MKTC_TAF_RESERVE_FREE_RENDER_FINISHED)
+#define MKTC_TAF_RESERVE_FREE_DUMMY_RENDER             0xAD00170B
+MKTC_ST(MKTC_TAF_RESERVE_FREE_DUMMY_RENDER)
+#define MKTC_TAF_DEBUG_SAS                                             0xAD00170C
+MKTC_ST(MKTC_TAF_DEBUG_SAS)
+#define MKTC_TAFINISHED_NOCONTEXTSWITCH                        0xAD00170D
+MKTC_ST(MKTC_TAFINISHED_NOCONTEXTSWITCH)
+
+#define MKTC_TAFINISHED_TERM_COMPLETE_START            0xAD001710
+MKTC_ST(MKTC_TAFINISHED_TERM_COMPLETE_START)
+#define MKTC_TAFINISHED_TERM_COMPLETE_END              0xAD001711
+MKTC_ST(MKTC_TAFINISHED_TERM_COMPLETE_END)
+
+#define MKTC_TAFINISHED_DPMPAGERECYCLING               0xAD001720
+MKTC_ST(MKTC_TAFINISHED_DPMPAGERECYCLING)
+
+#define MKTC_2DEVENT_2DCOMPLETE                                        0xAD001800
+MKTC_ST(MKTC_2DEVENT_2DCOMPLETE)
+#define MKTC_2DEVENT_END                                               0xAD001801
+MKTC_ST(MKTC_2DEVENT_END)
+#define        MKTC_2DLB_2DCOMPLETE                                    0xAD001802
+MKTC_ST(MKTC_2DLB_2DCOMPLETE)
+#define MKTC_2DLB_FIND2D                                               0xAD001803
+MKTC_ST(MKTC_2DLB_FIND2D)
+#define MKTC_2DLB_END                                                  0xAD001804
+MKTC_ST(MKTC_2DLB_END)
+#define MKTC_2DCOMPLETE_START                                  0xAD001805
+MKTC_ST(MKTC_2DCOMPLETE_START)
+#define MKTC_2DCOMPLETE_END                                            0xAD001806
+MKTC_ST(MKTC_2DCOMPLETE_END)
+#define MKTC_KICK2D_START                                              0xAD001807
+MKTC_ST(MKTC_KICK2D_START)
+#define MKTC_KICK2D_END                                                        0xAD001808
+MKTC_ST(MKTC_KICK2D_END)
+#define MKTC_DUMMYPROC2D                                               0xAD001809
+MKTC_ST(MKTC_DUMMYPROC2D)
+#define MKTC_FTD_SRCREADOPSBLOCKED                             0xAD00180A
+MKTC_ST(MKTC_FTD_SRCREADOPSBLOCKED)
+#define MKTC_FTD_SRCWRITEOPSBLOCKED                            0xAD00180B
+MKTC_ST(MKTC_FTD_SRCWRITEOPSBLOCKED)
+#define MKTC_FTD_DSTREADOPSBLOCKED                             0xAD00180C
+MKTC_ST(MKTC_FTD_DSTREADOPSBLOCKED)
+#define MKTC_FTD_DSTWRITEOPSBLOCKED                            0xAD00180D
+MKTC_ST(MKTC_FTD_DSTWRITEOPSBLOCKED)
+#define MKTC_FTD_TA2D_OVERLAP_BLOCKED                  0xAD00180E
+MKTC_ST(MKTC_FTD_TA2D_OVERLAP_BLOCKED)
+#define MKTC_U2DSO_UPDATEREADOPS                               0xAD00180F
+MKTC_ST(MKTC_U2DSO_UPDATEREADOPS)
+#define MKTC_U2DSO_UPDATEWRITEOPS                              0xAD001810
+MKTC_ST(MKTC_U2DSO_UPDATEWRITEOPS)
+#define MKTC_FTD_TAOPSBLOCKED                                  0xAD001811
+MKTC_ST(MKTC_FTD_TAOPSBLOCKED)
+#define MKTC_KICK2D_2DSLAVEPORT                                        0xAD001812
+MKTC_ST(MKTC_KICK2D_2DSLAVEPORT)
+#define MKTC_KICK2D_2DSLAVEPORT_DONE                   0xAD001813
+MKTC_ST(MKTC_KICK2D_2DSLAVEPORT_DONE)
+#define MKTC_FTD_CONTEXT_SUSPENDED                             0xAD001814
+MKTC_ST(MKTC_FTD_CONTEXT_SUSPENDED)
+#define MKTC_KICK2D_PID                                                        0xAD001815
+MKTC_ST(MKTC_KICK2D_PID)
+#define MKTC_FIND2D_ADDR_SPACE_DIFFERENT               0xAD001816
+MKTC_ST(MKTC_FIND2D_ADDR_SPACE_DIFFERENT)
+#define MKTC_FTD_3DOPSBLOCKED                                  0xAD001817
+MKTC_ST(MKTC_FTD_3DOPSBLOCKED)
+#define MKTC_FTD_DSTREADOPS2BLOCKED                            0xAD001818
+MKTC_ST(MKTC_FTD_DSTREADOPS2BLOCKED)
+
+#define MKTC_FCM_START                                                 0xAD001900
+MKTC_ST(MKTC_FCM_START)
+#define MKTC_FCM_END                                                   0xAD001901
+MKTC_ST(MKTC_FCM_END)
+
+#define MKTC_TIMER_ACTIVE_POWER                                        0xAD001A00
+MKTC_ST(MKTC_TIMER_ACTIVE_POWER)
+#define MKTC_TIMER_POWER_3D_ACTIVE                             0xAD001A01
+MKTC_ST(MKTC_TIMER_POWER_3D_ACTIVE)
+#define MKTC_TIMER_POWER_TA_ACTIVE                             0xAD001A02
+MKTC_ST(MKTC_TIMER_POWER_TA_ACTIVE)
+#define MKTC_TIMER_POWER_2D_ACTIVE                             0xAD001A03
+MKTC_ST(MKTC_TIMER_POWER_2D_ACTIVE)
+#define MKTC_TIMER_POWER_PENDING_EVENTS                        0xAD001A04
+MKTC_ST(MKTC_TIMER_POWER_PENDING_EVENTS)
+#define MKTC_TIMER_POWER_IDLE                                  0xAD001A05
+MKTC_ST(MKTC_TIMER_POWER_IDLE)
+#define MKTC_TIMER_POWER_OFF                                   0xAD001A06
+MKTC_ST(MKTC_TIMER_POWER_OFF)
+#define        MKTC_TIMER_POWER_CCB_ERROR                              0xAD001A07
+MKTC_ST(MKTC_TIMER_POWER_CCB_ERROR)
+#define        MKTC_TIMER_POWER_RESTART_IMMEDIATE              0xAD001A08
+MKTC_ST(MKTC_TIMER_POWER_RESTART_IMMEDIATE)
+
+#define MKTC_3DCONTEXT_SWITCH                                  0xAD001B00
+MKTC_ST(MKTC_3DCONTEXT_SWITCH)
+#define MKTC_3DCONTEXT_SWITCH_END                              0xAD001B01
+MKTC_ST(MKTC_3DCONTEXT_SWITCH_END)
+
+#define MKTC_TACONTEXT_SWITCH                                  0xAD001C00
+MKTC_ST(MKTC_TACONTEXT_SWITCH)
+#define MKTC_TACONTEXT_SWITCH_END                              0xAD001C02
+MKTC_ST(MKTC_TACONTEXT_SWITCH_END)
+
+#define MKTC_GETMISCINFO_MEMREAD_START                 0xAD001D00
+MKTC_ST(MKTC_GETMISCINFO_MEMREAD_START)
+#define MKTC_GETMISCINFO_MEMREAD_END                   0xAD001D01
+MKTC_ST(MKTC_GETMISCINFO_MEMREAD_END)
+#define MKTC_GETMISCINFO_MEMWRITE_START                        0xAD001D02
+MKTC_ST(MKTC_GETMISCINFO_MEMWRITE_START)
+#define MKTC_GETMISCINFO_MEMWRITE_END                  0xAD001D03
+MKTC_ST(MKTC_GETMISCINFO_MEMWRITE_END)
+
+#define        MKTC_HALTTA                                                             0xAD001E00
+MKTC_ST(MKTC_HALTTA)
+#define MKTC_HTA_SET_FLAG                                              0xAD001E01
+MKTC_ST(MKTC_HTA_SET_FLAG)
+#define MKTC_HTA_SAVE_COMPLEX_PTR                              0xAD001E02
+MKTC_ST(MKTC_HTA_SAVE_COMPLEX_PTR)
+#define MKTC_HALTTA_END                                                        0xAD001E03
+MKTC_ST(MKTC_HALTTA_END)
+
+#define        MKTC_RESUMETA                                                   0xAD001F00
+MKTC_ST(MKTC_RESUMETA)
+#define        MKTC_RTA_CONTEXT_LOADED                                 0xAD001F01
+MKTC_ST(MKTC_RTA_CONTEXT_LOADED)
+#define        MKTC_RTA_MTE_STATE_KICKED                               0xAD001F02
+MKTC_ST(MKTC_RTA_MTE_STATE_KICKED)
+#define MKTC_RTA_CMPLX_GEOM_PRESENT                            0xAD001F03
+MKTC_ST(MKTC_RTA_CMPLX_GEOM_PRESENT)
+#define        MKTC_RTA_CMPLX_STATE_KICKED                             0xAD001F04
+MKTC_ST(MKTC_RTA_CMPLX_STATE_KICKED)
+#define        MKTC_RTA_CHECK_NEXT_SA_PROG                             0xAD001F05
+MKTC_ST(MKTC_RTA_CHECK_NEXT_SA_PROG)
+#define MKTC_RTA_CORE_COMPLETED                                        0xAD001F06
+MKTC_ST(MKTC_RTA_CORE_COMPLETED)
+#define MKTC_RTA_DEBUG_SAS                                             0xAD001F07
+MKTC_ST(MKTC_RTA_DEBUG_SAS)
+#define MKTC_RESUMETA_END                                              0xAD001F0F
+MKTC_ST(MKTC_RESUMETA_END)
+
+#define MKTC_RENDERHALT                                                        0xAD002000
+MKTC_ST(MKTC_RENDERHALT)
+#define MKTC_RH_CLEARFLAGS                                             0xAD002001
+MKTC_ST(MKTC_RH_CLEARFLAGS)
+#define MKTC_RH_CTRL_ADDR                                              0xAD002002
+MKTC_ST(MKTC_RH_CTRL_ADDR)
+#define MKTC_RH_RGN_ADDR                                               0xAD002003
+MKTC_ST(MKTC_RH_RGN_ADDR)
+#define MKTC_RH_EMPTY_TILE                                             0xAD002004
+MKTC_ST(MKTC_RH_EMPTY_TILE)
+#define MKTC_RH_EMPTY_LAST_TILE                                        0xAD002005
+MKTC_ST(MKTC_RH_EMPTY_LAST_TILE)
+#define MKTC_RH_3D_TIMEOUT                                             0xAD002006
+MKTC_ST(MKTC_RH_3D_TIMEOUT)
+#define MKTC_RH_NOT_EMPTY                                              0xAD002007
+MKTC_ST(MKTC_RH_NOT_EMPTY)
+#define MKTC_RH_OBJECT_COMPLETE                                        0xAD002008
+MKTC_ST(MKTC_RH_OBJECT_COMPLETE)
+#define MKTC_RH_STREAM_LINK                                            0xAD002009
+MKTC_ST(MKTC_RH_STREAM_LINK)
+#define MKTC_RH_OBJECT_INCOMPLETE                              0xAD00200A
+MKTC_ST(MKTC_RH_OBJECT_INCOMPLETE)
+#define MKTC_RH_PRIM_MASK_PRESENT                              0xAD00200B
+MKTC_ST(MKTC_RH_PRIM_MASK_PRESENT)
+#define MKTC_RH_BYTE_MASK_PRESENT                              0xAD00200C
+MKTC_ST(MKTC_RH_BYTE_MASK_PRESENT)
+#define MKTC_RH_BYTE_MASK_ZERO                                 0xAD00200D
+MKTC_ST(MKTC_RH_BYTE_MASK_ZERO)
+#define MKTC_RH_PRIM_MASK_ZERO                                 0xAD00200E
+MKTC_ST(MKTC_RH_PRIM_MASK_ZERO)
+#define MKTC_RH_INVALIDATE_OBJECTS                             0xAD00200F
+MKTC_ST(MKTC_RH_INVALIDATE_OBJECTS)
+#define MKTC_RH_OBJECTS_INVALIDATED                            0xAD002010
+MKTC_ST(MKTC_RH_OBJECTS_INVALIDATED)
+#define MKTC_RH_DPM_RGN_PARSER_IDLE                            0xAD002011
+MKTC_ST(MKTC_RH_DPM_RGN_PARSER_IDLE)
+#define MKTC_RH_NEXT_RGN_BASE                                  0xAD002012
+MKTC_ST(MKTC_RH_NEXT_RGN_BASE)
+#define MKTC_RH_OCC_EXIT                                               0xAD002013
+MKTC_ST(MKTC_RH_OCC_EXIT)
+#define MKTC_RH_STILL_RUNNING                                  0xAD002020
+MKTC_ST(MKTC_RH_STILL_RUNNING)
+#define MKTC_RH_CLEARMCI                                               0xAD002021
+MKTC_ST(MKTC_RH_CLEARMCI)
+#define MKTC_RH_EOR                                                            0xAD002022
+MKTC_ST(MKTC_RH_EOR)
+#define MKTC_RENDERHALT_END                                            0xAD002030
+MKTC_ST(MKTC_RENDERHALT_END)
+
+#define        MKTC_FIND3D_POWERREQUEST                                0xAD002100
+MKTC_ST(MKTC_FIND3D_POWERREQUEST)
+
+#define        MKTC_FIND2D_POWERREQUEST                                0xAD002200
+MKTC_ST(MKTC_FIND2D_POWERREQUEST)
+
+#define        MKTC_UKERNEL_INIT                                               0xAD002300
+MKTC_ST(MKTC_UKERNEL_INIT)
+#define MKTC_UKERNEL_INIT_DCS_COMPLETE                 0xAD002301
+MKTC_ST(MKTC_UKERNEL_INIT_DCS_COMPLETE)
+#define MKTC_UKERNEL_INIT_VDMKICK_COMPLETE             0xAD002303
+MKTC_ST(MKTC_UKERNEL_INIT_VDMKICK_COMPLETE)
+
+#define MKTC_KICKTRANSFERRENDER_START                  0xAD002400
+MKTC_ST(MKTC_KICKTRANSFERRENDER_START)
+#define MKTC_KICKTRANSFERRENDER_ISP_START              0xAD002401
+MKTC_ST(MKTC_KICKTRANSFERRENDER_ISP_START)
+#define MKTC_KICKTRANSFERRENDER_END                            0xAD002402
+MKTC_ST(MKTC_KICKTRANSFERRENDER_END)
+#define MKTC_DUMMYPROCTRANSFER                                 0xAD002403
+MKTC_ST(MKTC_DUMMYPROCTRANSFER)
+#define MKTC_KTR_TQFENCE                                               0xAD002404
+MKTC_ST(MKTC_KTR_TQFENCE)
+#define MKTC_KICKTRANSFERRENDER_PID                            0xAD002405
+MKTC_ST(MKTC_KICKTRANSFERRENDER_PID)
+
+#define MKTC_HOSTKICK_CLEANUP_RT                               0xAD002500
+MKTC_ST(MKTC_HOSTKICK_CLEANUP_RT)
+#define MKTC_HOSTKICK_CLEANUP_RC                               0xAD002501
+MKTC_ST(MKTC_HOSTKICK_CLEANUP_RC)
+#define MKTC_HOSTKICK_CLEANUP_TC                               0xAD002502
+MKTC_ST(MKTC_HOSTKICK_CLEANUP_TC)
+#define MKTC_HOSTKICK_CLEANUP_2DC                              0xAD002503
+MKTC_ST(MKTC_HOSTKICK_CLEANUP_2DC)
+#define MKTC_HOSTKICK_CLEANUP_PB                               0xAD002504
+MKTC_ST(MKTC_HOSTKICK_CLEANUP_PB)
+#define MKTC_HOSTKICK_GETMISCINFO                              0xAD002505
+MKTC_ST(MKTC_HOSTKICK_GETMISCINFO)
+#define MKTC_HOSTKICK_DATABREAKPOINT                   0xAD002506
+MKTC_ST(MKTC_HOSTKICK_DATABREAKPOINT)
+#define MKTC_HOSTKICK_SETHWPERFSTATUS                  0xAD002507
+MKTC_ST(MKTC_HOSTKICK_SETHWPERFSTATUS)
+
+#define MKTC_ZEROPC                                                            0xAD002600
+MKTC_ST(MKTC_ZEROPC)
+
+#define MKTC_ASSERT_FAIL                                               0xAD002700
+MKTC_ST(MKTC_ASSERT_FAIL)
+
+#define MKTC_SDLB_ILLEGAL                                              0xAD002800
+MKTC_ST(MKTC_SDLB_ILLEGAL)
+
+#define MKTC_SPMEVENT_OUTOFMEM                                 0xAD002901
+MKTC_ST(MKTC_SPMEVENT_OUTOFMEM)
+#define MKTC_SPMEVENT_TATERMINATE                              0xAD002902
+MKTC_ST(MKTC_SPMEVENT_TATERMINATE)
+#define MKTC_SPMEVENT_END                                              0xAD002904
+MKTC_ST(MKTC_SPMEVENT_END)
+
+#define MKTC_SPMLB_OUTOFMEM                                            0xAD002981
+MKTC_ST(MKTC_SPMLB_OUTOFMEM)
+#define MKTC_SPMLB_TATERMINATE                                 0xAD002982
+MKTC_ST(MKTC_SPMLB_TATERMINATE)
+#define MKTC_SPMLB_SPMRENDERFINSHED                            0xAD002983
+MKTC_ST(MKTC_SPMLB_SPMRENDERFINSHED)
+#define MKTC_SPMLB_END                                                 0xAD002985
+MKTC_ST(MKTC_SPMLB_END)
+
+#define MKTC_SPM_CHECK_MT_DEADLOCK                             0xAD002991
+MKTC_ST(MKTC_SPM_CHECK_MT_DEADLOCK)
+#define MKTC_SPM_CHECK_GLOBAL_DEADLOCK                 0xAD002992
+MKTC_ST(MKTC_SPM_CHECK_GLOBAL_DEADLOCK)
+#define MKTC_SPM_RESERVE_ADDED                                 0xAD002993
+MKTC_ST(MKTC_SPM_RESERVE_ADDED)
+#define MKTC_SPM_FORCE_GLOBAL_OOM_FAILED               0xAD00299E
+MKTC_ST(MKTC_SPM_FORCE_GLOBAL_OOM_FAILED)
+#define MKTC_SPM_DEADLOCK_MEM_FAILED                   0xAD00299F
+MKTC_ST(MKTC_SPM_DEADLOCK_MEM_FAILED)
+
+#define MKTC_IBC_ILLEGAL                                               0xAD002A00
+MKTC_ST(MKTC_IBC_ILLEGAL)
+
+#define MKTC_HWP_CLEARCOUNTERS                                 0xAD002B00
+MKTC_ST(MKTC_HWP_CLEARCOUNTERS)
+
+#define MKTC_TA_FRAMENUM                                               0xAD002C00
+MKTC_ST(MKTC_TA_FRAMENUM)
+#define MKTC_3D_FRAMENUM                                               0xAD002C01
+MKTC_ST(MKTC_3D_FRAMENUM)
+#define MKTC_SPM3D_FRAMENUM                                            0xAD002C02
+MKTC_ST(MKTC_SPM3D_FRAMENUM)
+
+#define MKTC_HKTA_RENDERCONTEXT                                        0xAD002D00
+MKTC_ST(MKTC_HKTA_RENDERCONTEXT)
+#define MKTC_IDLECORE_REFCOUNT_FAIL                            0xAD002E00
+MKTC_ST(MKTC_IDLECORE_REFCOUNT_FAIL)
+
+#define MKTC_MCISTATE_NOT_CLEARED                              0xAD002F00
+MKTC_ST(MKTC_MCISTATE_NOT_CLEARED)
+
+#define MKTC_LOWERED_TO_PDS_THRESHOLD                          0xAD003000
+MKTC_ST(MKTC_LOWERED_TO_PDS_THRESHOLD)
+#define MKTC_REDUCE_MAX_VTX_PARTITIONS                         0xAD003001
+MKTC_ST(MKTC_REDUCE_MAX_VTX_PARTITIONS)
+#define MKTC_KTAOVERRIDE_MAX_VTX_PARTITIONS                    0xAD003002
+MKTC_ST(MKTC_KTAOVERRIDE_MAX_VTX_PARTITIONS)
+#define MKTC_KTANOOVERRIDE_MAX_VTX_PARTITIONS                  0xAD003003
+MKTC_ST(MKTC_KTANOOVERRIDE_MAX_VTX_PARTITIONS)
+
+#define MKTC_IPRB_NORENDERDETAILS                              0xAD003010
+MKTC_ST(MKTC_IPRB_NORENDERDETAILS)
+#define MKTC_IPRB_HAVERENDERDETAILS                            0xAD003011
+MKTC_ST(MKTC_IPRB_HAVERENDERDETAILS)
+
+#define MKTC_RENDER_OUT_OF_ORDER                               0xAD003020
+MKTC_ST(MKTC_RENDER_OUT_OF_ORDER)
+#define MKTC_RENDER_NOT_OUT_OF_ORDER                   0xAD003021
+MKTC_ST(MKTC_RENDER_NOT_OUT_OF_ORDER)
+
+#define MKTC_ZLS_IDLE_BEGIN                                            0xAD003030
+MKTC_ST(MKTC_ZLS_IDLE_BEGIN)
+#define MKTC_ZLS_ISP_CLK_GATING_EN                             0xAD003031
+MKTC_ST(MKTC_ZLS_ISP_CLK_GATING_EN)
+#define MKTC_ZLS_IDLE_END                                              0xAD003032
+MKTC_ST(MKTC_ZLS_IDLE_END)
+
+#endif /*  __SGX_UKERNEL_STATUS_CODES_H__ */
+
+/******************************************************************************
+ End of file (sgx_ukernel_status_codes.h)
+******************************************************************************/
index 5a45c5c..17f6d95 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          sgx services structures/functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    inline functions/structures shared across UM and KM services components
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #if !defined (__SGXINFO_H__)
 #define __SGXINFO_H__
 
@@ -157,7 +172,7 @@ typedef struct _SGX_BRIDGE_INIT_INFO_
 #endif
 #endif
 
-#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31425)
+#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31559)
        IMG_HANDLE      hKernelVDMSnapShotBufferMemInfo;
        IMG_HANDLE      hKernelVDMCtrlStreamBufferMemInfo;
 #endif
@@ -185,7 +200,7 @@ typedef struct _SGX_BRIDGE_INIT_INFO_
        IMG_UINT32 ui32MasterClkGateStatusMask;
        IMG_UINT32 ui32MasterClkGateStatus2Reg;
        IMG_UINT32 ui32MasterClkGateStatus2Mask;
-#endif 
+#endif /* SGX_FEATURE_MP */
 
        IMG_UINT32 ui32CacheControl;
 
@@ -215,7 +230,7 @@ typedef struct _SGX_DEVICE_SYNC_LIST_
 
        struct _SGX_DEVICE_SYNC_LIST_   *psNext;
 
-       
+       /* Must be the last variable in the structure */
        IMG_UINT32                      ui32NumSyncObjects;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                         ahSyncHandles[1];
@@ -252,7 +267,7 @@ typedef struct _SGX_CCB_KICK_
        IMG_HANDLE      hKernelHWSyncListMemInfo;
 #endif
 
-       
+       /* DST syncs */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID         *pahDstSyncHandles;
 #else
@@ -276,16 +291,16 @@ typedef struct _SGX_CCB_KICK_
 #endif
 
        IMG_BOOL        bFirstKickOrResume;
-#if (defined(NO_HARDWARE) || defined(PDUMP))
+#if defined(NO_HARDWARE) || defined(PDUMP)
        IMG_BOOL        bTerminateOrAbort;
 #endif
        IMG_BOOL        bLastInScene;
 
-       
+       /* CCB offset of data structure associated with this kick */
        IMG_UINT32      ui32CCBOffset;
 
 #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS)
-       
+       /* SRC and DST syncs */
        IMG_UINT32      ui32NumTASrcSyncs;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID         ahTASrcKernelSyncInfo[SGX_MAX_TA_SRC_SYNCS];
@@ -305,16 +320,16 @@ typedef struct _SGX_CCB_KICK_
        IMG_HANDLE      ah3DSrcKernelSyncInfo[SGX_MAX_3D_SRC_SYNCS];
 #endif
 #else
-       
+       /* SRC syncs */
        IMG_UINT32      ui32NumSrcSyncs;
 #if defined (SUPPORT_SID_INTERFACE)
-       IMG_SID         ahSrcKernelSyncInfo[SGX_MAX_SRC_SYNCS];
+       IMG_SID         ahSrcKernelSyncInfo[SGX_MAX_SRC_SYNCS_TA];
 #else
-       IMG_HANDLE      ahSrcKernelSyncInfo[SGX_MAX_SRC_SYNCS];
+       IMG_HANDLE      ahSrcKernelSyncInfo[SGX_MAX_SRC_SYNCS_TA];
 #endif
 #endif
 
-       
+       /* TA/3D dependency data */
        IMG_BOOL        bTADependency;
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID         hTA3DSyncInfo;
@@ -337,19 +352,31 @@ typedef struct _SGX_CCB_KICK_
 } SGX_CCB_KICK;
 
 
+/*!
+ ******************************************************************************
+ * shared client/kernel device information structure for SGX
+ *****************************************************************************/
 #define SGX_KERNEL_USE_CODE_BASE_INDEX         15
 
 
+/*!
+ ******************************************************************************
+ * Client device information structure for SGX
+ *****************************************************************************/
 typedef struct _SGX_CLIENT_INFO_
 {
-       IMG_UINT32                                      ui32ProcessID;                  
-       IMG_VOID                                        *pvProcess;                             
-       PVRSRV_MISC_INFO                        sMiscInfo;                              
+       IMG_UINT32                                      ui32ProcessID;                  /*!< ID of process controlling SGX device */
+       IMG_VOID                                        *pvProcess;                             /*!< pointer to OS specific 'process' structure */
+       PVRSRV_MISC_INFO                        sMiscInfo;                              /*!< Misc. Information, inc. SOC specifics */
 
        IMG_UINT32                                      asDevData[SGX_MAX_DEV_DATA];
 
 } SGX_CLIENT_INFO;
 
+/*!
+ ******************************************************************************
+ * Internal device information structure for SGX
+ *****************************************************************************/
 typedef struct _SGX_INTERNAL_DEVINFO_
 {
        IMG_UINT32                      ui32Flags;
@@ -429,24 +456,24 @@ typedef struct _PVRSRV_2D_SGX_KICK_
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID                 ahSrcSyncInfo[SGX_MAX_2D_SRC_SYNC_OPS];
 
-       
+       /* need to be able to check reads and writes on dest, and update writes */
        IMG_SID                 hDstSyncInfo;
 
-       
+       /* need to be able to check reads and writes on TA ops, and update writes */
        IMG_SID                 hTASyncInfo;
 
-       
+       /* need to be able to check reads and writes on 2D ops, and update writes */
        IMG_SID                 h3DSyncInfo;
 #else
        IMG_HANDLE              ahSrcSyncInfo[SGX_MAX_2D_SRC_SYNC_OPS];
 
-       
+       /* need to be able to check reads and writes on dest, and update writes */
        IMG_HANDLE              hDstSyncInfo;
 
-       
+       /* need to be able to check reads and writes on TA ops, and update writes */
        IMG_HANDLE              hTASyncInfo;
 
-       
+       /* need to be able to check reads and writes on 2D ops, and update writes */
        IMG_HANDLE              h3DSyncInfo;
 #endif
 
@@ -456,8 +483,11 @@ typedef struct _PVRSRV_2D_SGX_KICK_
 #endif
        IMG_HANDLE              hDevMemContext;
 } PVRSRV_2D_SGX_KICK, *PPVRSRV_2D_SGX_KICK;
-#endif 
-#endif 
+#endif /* defined(SGX_FEATURE_2D_HARDWARE) */
+#endif /* defined(TRANSFER_QUEUE) */
 
 
-#endif 
+#endif /* __SGXINFO_H__ */
+/******************************************************************************
+ End of file (sgxinfo.h)
+******************************************************************************/
index 329b81a..9b38583 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PVR Common Bridge Module (kernel side)
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Receives calls from the user portion of services and
+                despatches them to functions in the kernel portion.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 
 
@@ -46,6 +63,7 @@
 #include "perproc.h"
 #include "device.h"
 #include "buffer_manager.h"
+#include "refcount.h"
 
 #include "pdump_km.h"
 #include "syscommon.h"
 
 #include "srvkm.h"
 
+/* FIXME: we should include an OS specific header here to allow configuration of
+ * which functions should be excluded (like the shared srvclient bridge code)
+ * so that ports may choose to override certain things. */
+
+/* For the purpose of maintainability, it is intended that this file should not
+ * contain large amounts of OS specific #ifdefs. Headers are fine, and perhaps
+ * a few one liners, but for anything more, please find a way to add e.g.
+ * an osfunc.c abstraction or override the entire function in question within
+ * env,*,pvr_bridge_k.c
+ */
+
+
 PVRSRV_BRIDGE_DISPATCH_TABLE_ENTRY g_BridgeDispatchTable[BRIDGE_DISPATCH_TABLE_ENTRY_COUNT];
 
 #if defined(DEBUG_BRIDGE_KM)
@@ -147,7 +177,10 @@ PVRSRVAcquireDeviceDataBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /*
+        * Handle is not allocated in batch mode, as there is no resource
+        * allocation to undo if the handle allocation fails.
+        */
                psAcquireDevInfoOUT->eError =
                PVRSRVAllocHandle(psPerProc->psHandleBase,
                                                  &psAcquireDevInfoOUT->hDevCookie,
@@ -175,7 +208,10 @@ PVRSRVCreateDeviceMemContextBW(IMG_UINT32 ui32BridgeID,
 
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_CREATE_DEVMEMCONTEXT);
 
-       
+       /*
+        * We potentially need one handle for the device memory context,
+        * and one handle for each client heap.
+        */
        NEW_HANDLE_BATCH_OR_ERROR(psCreateDevMemContextOUT->eError, psPerProc, PVRSRV_MAX_CLIENT_HEAPS + 1)
 
        psCreateDevMemContextOUT->eError =
@@ -206,7 +242,11 @@ PVRSRVCreateDeviceMemContextBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /*
+        * Only allocate a handle if the device memory context was created.
+        * If an existing context was returned, lookup the existing
+        * handle.
+        */
        if(bCreated)
        {
                PVRSRVAllocHandleNR(psPerProc->psHandleBase,
@@ -240,7 +280,13 @@ PVRSRVCreateDeviceMemContextBW(IMG_UINT32 ui32BridgeID,
                if(abSharedDeviceMemHeap[i])
 #endif
                {
-                       
+                       /*
+                        * Heaps shared by everybody.  These heaps are not
+                        * created as part of the device memory context
+                        * creation, and exist for the lifetime of the
+                        * driver, hence, we use shared handles for these
+                        * heaps.
+                        */
 #if defined (SUPPORT_SID_INTERFACE)
                        PVRSRVAllocHandleNR(psPerProc->psHandleBase,
                                                                &hDevMemHeapExt,
@@ -257,7 +303,12 @@ PVRSRVCreateDeviceMemContextBW(IMG_UINT32 ui32BridgeID,
 #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)
                else
                {
-                       
+                       /*
+                        * Heaps belonging to this context.  The handles for
+                        * these are made subhandles of the memory context
+                        * handle, so that they are automatically deallocated
+                        * when the memory context handle is deallocated.
+                        */
                        if(bCreated)
                        {
 #if defined (SUPPORT_SID_INTERFACE)
@@ -425,7 +476,13 @@ PVRSRVGetDeviceMemHeapInfoBW(IMG_UINT32 ui32BridgeID,
                if(abSharedDeviceMemHeap[i])
 #endif
                {
-                       
+                       /*
+                        * Heaps shared by everybody.  These heaps are not
+                        * created as part of the device memory context
+                        * creation, and exist for the lifetime of the
+                        * driver, hence, we use shared handles for these
+                        * heaps.
+                        */
 #if defined (SUPPORT_SID_INTERFACE)
                        PVRSRVAllocHandleNR(psPerProc->psHandleBase,
                                                                &hDevMemHeapExt,
@@ -442,7 +499,12 @@ PVRSRVGetDeviceMemHeapInfoBW(IMG_UINT32 ui32BridgeID,
 #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)
                else
                {
-                       
+                       /*
+                        * Heaps belonging to this context.  The handles for
+                        * these are made subhandles of the memory context
+                        * handle, so that they are automatically deallocated
+                        * when the memory context handle is deallocated.
+                        */
                        psGetDevMemHeapInfoOUT->eError =
                                PVRSRVFindHandle(psPerProc->psHandleBase,
                                                                 &hDevMemHeapExt,
@@ -475,6 +537,7 @@ PVRSRVGetDeviceMemHeapInfoBW(IMG_UINT32 ui32BridgeID,
 
 
 #if defined(OS_PVRSRV_ALLOC_DEVICE_MEM_BW)
+/* customised version */
 IMG_INT
 PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
                                           PVRSRV_BRIDGE_IN_ALLOCDEVICEMEM *psAllocDeviceMemIN,
@@ -492,11 +555,30 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
        IMG_HANDLE hDevMemHeapInt;
        IMG_UINT32 ui32ShareIndex;
        IMG_BOOL bUseShareMemWorkaround;
+       IMG_BOOL *pabMapChunk = IMG_NULL;
 
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_ALLOC_DEVICEMEM);
 
        NEW_HANDLE_BATCH_OR_ERROR(psAllocDeviceMemOUT->eError, psPerProc, 2)
 
+       /* Do same sanity checking */
+       if (psAllocDeviceMemIN->ui32Attribs & PVRSRV_MEM_SPARSE)
+       {
+               if (psAllocDeviceMemIN->ui32NumPhysChunks > psAllocDeviceMemIN->ui32NumVirtChunks)
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVAllocDeviceMemBW: more physical chunks then virtual space"));
+                       psAllocDeviceMemOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
+                       return 0;
+               }
+       
+               if (psAllocDeviceMemIN->pabMapChunk == IMG_NULL)
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVAllocDeviceMemBW: Called in sparse mapping mode but without MapChunk array"));
+                       psAllocDeviceMemOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
+                       return 0;
+               }
+       }
+
        psAllocDeviceMemOUT->eError =
                PVRSRVLookupHandle(psPerProc->psHandleBase, &hDevCookieInt,
                                                   psAllocDeviceMemIN->hDevCookie,
@@ -517,15 +599,17 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* Memory sharing workaround, version 2 */
 
        bUseShareMemWorkaround = ((psAllocDeviceMemIN->ui32Attribs & PVRSRV_MEM_XPROC) != 0) ? IMG_TRUE : IMG_FALSE;
-       ui32ShareIndex = 7654321; 
+       ui32ShareIndex = 7654321; /* stops MSVC compiler warning */
 
        if (bUseShareMemWorkaround)
        {
-               
-               
+               /* allocate a shared-surface ID, prior to the call to AllocDeviceMem */
+               /* We could plumb in an extra argument, but for now, we'll keep the
+                  shared-surface ID as a piece of global state, and rely upon the
+                  bridge mutex to make it safe for us */
 
                psAllocDeviceMemOUT->eError =
                        BM_XProcWorkaroundFindNewBufferAndSetShareIndex(&ui32ShareIndex);
@@ -535,6 +619,54 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
                }
        }
 
+       /* Check access to private data, if provided */
+       if(psAllocDeviceMemIN->pvPrivData)
+       {
+               if(!OSAccessOK(PVR_VERIFY_READ,
+                                          psAllocDeviceMemIN->pvPrivData,
+                                          psAllocDeviceMemIN->ui32PrivDataLength))
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVAllocDeviceMemBW: Access check failed for pvPrivData"));
+                       return -EFAULT;
+               }
+       }
+
+       if (psAllocDeviceMemIN->ui32Attribs & PVRSRV_MEM_SPARSE)
+       {
+               /* Check access to the sparse mapping table, if provided */
+               if(!OSAccessOK(PVR_VERIFY_READ,
+                                          psAllocDeviceMemIN->pabMapChunk,
+                                          psAllocDeviceMemIN->ui32NumVirtChunks))
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVAllocDeviceMemBW: Access check failed for pabMapChunk"));
+                       return -EFAULT;
+               }
+
+               psAllocDeviceMemOUT->eError = OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                                                                                sizeof(IMG_BOOL) * psAllocDeviceMemIN->ui32NumVirtChunks,
+                                                                                                (IMG_VOID **) &pabMapChunk,
+                                                                                                0,
+                                                                                                "MapChunk kernel copy");
+               if (psAllocDeviceMemOUT->eError != PVRSRV_OK)
+               {
+                       return 0;
+               }
+
+               psAllocDeviceMemOUT->eError = OSCopyFromUser(psPerProc,
+                                                                                                        pabMapChunk,
+                                                                                                        psAllocDeviceMemIN->pabMapChunk,
+                                                                                                        sizeof(IMG_BOOL) * psAllocDeviceMemIN->ui32NumVirtChunks);
+               if (psAllocDeviceMemOUT->eError != PVRSRV_OK)
+               {
+                       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                         sizeof(IMG_BOOL) * psAllocDeviceMemIN->ui32NumVirtChunks,
+                                         pabMapChunk,
+                                         0);
+                       return 0;
+               }
+       }
+
+
        psAllocDeviceMemOUT->eError =
                PVRSRVAllocDeviceMemKM(hDevCookieInt,
                                                           psPerProc,
@@ -542,8 +674,14 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
                                                           psAllocDeviceMemIN->ui32Attribs,
                                                           psAllocDeviceMemIN->ui32Size,
                                                           psAllocDeviceMemIN->ui32Alignment,
+                                                          psAllocDeviceMemIN->pvPrivData,
+                                                          psAllocDeviceMemIN->ui32PrivDataLength,
+                                                          psAllocDeviceMemIN->ui32ChunkSize,
+                                                          psAllocDeviceMemIN->ui32NumVirtChunks,
+                                                          psAllocDeviceMemIN->ui32NumPhysChunks,
+                                                          pabMapChunk,
                                                           &psMemInfo,
-                                                          "" );
+                                                          "" /*FIXME: add something meaningful*/);
 
        if (bUseShareMemWorkaround)
        {
@@ -583,7 +721,7 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
        psAllocDeviceMemOUT->sClientMemInfo.ui32Flags = psMemInfo->ui32Flags;
        psAllocDeviceMemOUT->sClientMemInfo.uAllocSize = psMemInfo->uAllocSize;
 #if defined (SUPPORT_SID_INTERFACE)
-       
+       /* see below */
 #else
        psAllocDeviceMemOUT->sClientMemInfo.hMappingInfo = psMemInfo->sMemBlk.hOSMemHandle;
 #endif
@@ -614,7 +752,7 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
 
        if(psAllocDeviceMemIN->ui32Attribs & PVRSRV_MEM_NO_SYNCOBJ)
        {
-               
+               /* signal no syncinfo */
                OSMemSet(&psAllocDeviceMemOUT->sClientSyncInfo,
                                 0,
                                 sizeof (PVRSRV_CLIENT_SYNC_INFO));
@@ -622,7 +760,7 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
        }
        else
        {
-               
+               /* and setup the sync info */
 
 #if !defined(PVRSRV_DISABLE_UM_SYNCOBJ_MAPPINGS)
                psAllocDeviceMemOUT->sClientSyncInfo.psSyncData =
@@ -631,6 +769,8 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
                        psMemInfo->psKernelSyncInfo->sWriteOpsCompleteDevVAddr;
                psAllocDeviceMemOUT->sClientSyncInfo.sReadOpsCompleteDevVAddr =
                        psMemInfo->psKernelSyncInfo->sReadOpsCompleteDevVAddr;
+               psAllocDeviceMemOUT->sClientSyncInfo.sReadOps2CompleteDevVAddr =
+                       psMemInfo->psKernelSyncInfo->sReadOps2CompleteDevVAddr;
 
 #if defined (SUPPORT_SID_INTERFACE)
                if (psMemInfo->psKernelSyncInfo->psSyncDataMemInfoKM->sMemBlk.hOSMemHandle != IMG_NULL)
@@ -661,7 +801,6 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
 
                psAllocDeviceMemOUT->sClientMemInfo.psClientSyncInfo =
                        &psAllocDeviceMemOUT->sClientSyncInfo;
-
        }
 
        COMMIT_HANDLE_BATCH_OR_ERROR(psAllocDeviceMemOUT->eError, psPerProc)
@@ -669,7 +808,7 @@ PVRSRVAllocDeviceMemBW(IMG_UINT32 ui32BridgeID,
        return 0;
 }
 
-#endif 
+#endif /* OS_PVRSRV_ALLOC_DEVICE_MEM_BW */
 
 static IMG_INT
 PVRSRVFreeDeviceMemBW(IMG_UINT32 ui32BridgeID,
@@ -680,7 +819,6 @@ PVRSRVFreeDeviceMemBW(IMG_UINT32 ui32BridgeID,
        IMG_HANDLE hDevCookieInt;
        IMG_VOID *pvKernelMemInfo;
 
-
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_FREE_DEVICEMEM);
 
        psRetOUT->eError =
@@ -745,7 +883,7 @@ PVRSRVExportDeviceMemBW(IMG_UINT32 ui32BridgeID,
                           ui32BridgeID == PVRSRV_GET_BRIDGE_ID(PVRSRV_BRIDGE_EXPORT_DEVICEMEM_2));
        PVR_UNREFERENCED_PARAMETER(ui32BridgeID);
 
-       
+       /* find the device cookie */
        psExportDeviceMemOUT->eError =
         PVRSRVLookupHandle(psPerProc->psHandleBase,
                            &hDevCookieInt,
@@ -758,7 +896,7 @@ PVRSRVExportDeviceMemBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* find the kernel meminfo from the process handle list */
        psExportDeviceMemOUT->eError =
                PVRSRVLookupHandle(psPerProc->psHandleBase,
                                                   (IMG_PVOID *)&psKernelMemInfo,
@@ -775,7 +913,7 @@ PVRSRVExportDeviceMemBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* see if it's already exported */
        psExportDeviceMemOUT->eError =
                PVRSRVFindHandle(KERNEL_HANDLE_BASE,
                                                         &psExportDeviceMemOUT->hMemInfo,
@@ -783,12 +921,12 @@ PVRSRVExportDeviceMemBW(IMG_UINT32 ui32BridgeID,
                                                         PVRSRV_HANDLE_TYPE_MEM_INFO);
        if(psExportDeviceMemOUT->eError == PVRSRV_OK)
        {
-               
+               /* it's already exported */
                PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVExportDeviceMemBW: allocation is already exported"));
                return 0;
        }
 
-       
+       /* export the allocation */
        psExportDeviceMemOUT->eError = PVRSRVAllocHandle(KERNEL_HANDLE_BASE,
                                                                                                        &psExportDeviceMemOUT->hMemInfo,
                                                                                                        psKernelMemInfo,
@@ -800,7 +938,7 @@ PVRSRVExportDeviceMemBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* mark the meminfo as 'exported' */
        psKernelMemInfo->ui32Flags |= PVRSRV_MEM_EXPORTED;
 
        return 0;
@@ -823,7 +961,7 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
 
        NEW_HANDLE_BATCH_OR_ERROR(psMapDevMemOUT->eError, psPerProc, 2)
 
-       
+       /* lookup srcmeminfo handle */
        psMapDevMemOUT->eError = PVRSRVLookupHandle(KERNEL_HANDLE_BASE,
                                                                                                (IMG_VOID**)&psSrcKernelMemInfo,
                                                                                                psMapDevMemIN->hKernelMemInfo,
@@ -833,7 +971,7 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* lookup dev mem heap handle */
        psMapDevMemOUT->eError = PVRSRVLookupHandle(psPerProc->psHandleBase,
                                                                                                &hDstDevMemHeap,
                                                                                                psMapDevMemIN->hDstDevMemHeap,
@@ -843,19 +981,20 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* check for workaround */
        if (psSrcKernelMemInfo->sShareMemWorkaround.bInUse)
        {
                PVR_DPF((PVR_DBG_MESSAGE, "using the mem wrap workaround."));
 
-               
-
-
-
-
-
-
-
+               /* Ensure we get the same ID for this allocation, such that it
+                  inherits the same physical block.  Rather than add a lot of
+                  plumbing to several APIs, we call into buffer manager directly
+                  to set "global" state.  This works only if we make
+                  this allocation while holding the bridge mutex and don't
+                  make any other allocations (because the state persists and
+                  would affect other device memory allocations too).  It is
+                  important that we bracket the PVRSRVAllocDeviceMemKM() call
+                  with this Set/Unset pair. */
                psMapDevMemOUT->eError = BM_XProcWorkaroundSetShareIndex(psSrcKernelMemInfo->sShareMemWorkaround.ui32ShareIndex);
                if(psMapDevMemOUT->eError != PVRSRV_OK)
                {
@@ -870,27 +1009,32 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
                                                                   psSrcKernelMemInfo->sShareMemWorkaround.ui32OrigReqAttribs | PVRSRV_MEM_NO_SYNCOBJ,
                                                                   psSrcKernelMemInfo->sShareMemWorkaround.ui32OrigReqSize,
                                                                   psSrcKernelMemInfo->sShareMemWorkaround.ui32OrigReqAlignment,
+                                                                  IMG_NULL,
+                                                                  0,
+                                                                  /* FIXME: Do we need to be able to export sparse memory? */
+                                                                  0,0,0,IMG_NULL,      /* No sparse mapping data */
                                                                   &psDstKernelMemInfo,
-                                                                  "" );
-               
-
+                                                                  "" /*FIXME: add something meaningful*/);
+               /* counterpart of the above "SetShareIndex".  NB: this must be
+                  done in both the success and failure paths of the
+                  AllocDeviceMemKM() call */
                BM_XProcWorkaroundUnsetShareIndex(psSrcKernelMemInfo->sShareMemWorkaround.ui32ShareIndex);
                if(psMapDevMemOUT->eError != PVRSRV_OK)
                {
-                       PVR_DPF((PVR_DBG_ERROR, "lakjgfgewjlrgebhe"));
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVMapDeviceMemoryBW: Failed to create allocation for cross-process memory map"));
                        return 0;
                }
 
                if(psSrcKernelMemInfo->psKernelSyncInfo)
                {
-                       psSrcKernelMemInfo->psKernelSyncInfo->ui32RefCount++;
+                       PVRSRVKernelSyncInfoIncRef(psSrcKernelMemInfo->psKernelSyncInfo, psSrcKernelMemInfo);
                }
 
                psDstKernelMemInfo->psKernelSyncInfo = psSrcKernelMemInfo->psKernelSyncInfo;
        }
        else
        {
-               
+               /* map the meminfo to the target heap and memory context */
                psMapDevMemOUT->eError = PVRSRVMapDeviceMemoryKM(psPerProc,
                                                                                                                 psSrcKernelMemInfo,
                                                                                                                 hDstDevMemHeap,
@@ -901,7 +1045,7 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
                }
        }
 
-       
+       /* copy the workaround info */
        psDstKernelMemInfo->sShareMemWorkaround = psSrcKernelMemInfo->sShareMemWorkaround;
 
        OSMemSet(&psMapDevMemOUT->sDstClientMemInfo,
@@ -919,12 +1063,12 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
        psMapDevMemOUT->sDstClientMemInfo.ui32Flags = psDstKernelMemInfo->ui32Flags;
     psMapDevMemOUT->sDstClientMemInfo.uAllocSize = psDstKernelMemInfo->uAllocSize;
 #if defined (SUPPORT_SID_INTERFACE)
-       
+       /* see below */
 #else
        psMapDevMemOUT->sDstClientMemInfo.hMappingInfo = psDstKernelMemInfo->sMemBlk.hOSMemHandle;
 #endif
 
-       
+       /* allocate handle to the DST kernel meminfo */
        PVRSRVAllocHandleNR(psPerProc->psHandleBase,
                                          &psMapDevMemOUT->sDstClientMemInfo.hKernelMemInfo,
                                          psDstKernelMemInfo,
@@ -933,7 +1077,7 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
        psMapDevMemOUT->sDstClientSyncInfo.hKernelSyncInfo = IMG_NULL;
 
 #if defined (SUPPORT_SID_INTERFACE)
-       
+       /* alloc subhandle for the mapping info */
        if (psDstKernelMemInfo->sMemBlk.hOSMemHandle != IMG_NULL)
        {
                PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
@@ -949,7 +1093,7 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
        }
 #endif
 
-       
+       /* and setup the sync info */
        if(psDstKernelMemInfo->psKernelSyncInfo)
        {
 #if !defined(PVRSRV_DISABLE_UM_SYNCOBJ_MAPPINGS)
@@ -959,9 +1103,11 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
                        psDstKernelMemInfo->psKernelSyncInfo->sWriteOpsCompleteDevVAddr;
                psMapDevMemOUT->sDstClientSyncInfo.sReadOpsCompleteDevVAddr =
                        psDstKernelMemInfo->psKernelSyncInfo->sReadOpsCompleteDevVAddr;
+               psMapDevMemOUT->sDstClientSyncInfo.sReadOps2CompleteDevVAddr =
+                       psDstKernelMemInfo->psKernelSyncInfo->sReadOps2CompleteDevVAddr;
 
 #if defined (SUPPORT_SID_INTERFACE)
-               
+               /* alloc subhandle for the mapping info */
                if (psDstKernelMemInfo->psKernelSyncInfo->psSyncDataMemInfoKM->sMemBlk.hOSMemHandle != IMG_NULL)
                {
                        PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
@@ -982,7 +1128,11 @@ PVRSRVMapDeviceMemoryBW(IMG_UINT32 ui32BridgeID,
 #endif
 
                psMapDevMemOUT->sDstClientMemInfo.psClientSyncInfo = &psMapDevMemOUT->sDstClientSyncInfo;
-               
+               /*
+                * The sync info is associated with the device buffer,
+                * and not allocated here.  It isn't exported when created,
+                * hence the handle allocation rather than a lookup.
+                */
                PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
                                          &psMapDevMemOUT->sDstClientSyncInfo.hKernelSyncInfo,
                                          psDstKernelMemInfo->psKernelSyncInfo,
@@ -1067,7 +1217,11 @@ PVRSRVMapDeviceClassMemoryBW(IMG_UINT32 ui32BridgeID,
 
        NEW_HANDLE_BATCH_OR_ERROR(psMapDevClassMemOUT->eError, psPerProc, 2)
 
-       
+       /*
+        * The buffer to be mapped can belong to a 3rd party display or
+        * buffer driver, and we don't know which type we have at this
+        * point.
+        */
        psMapDevClassMemOUT->eError =
         PVRSRVLookupHandleAnyType(psPerProc->psHandleBase,
                                                                  &hDeviceClassBufferInt,
@@ -1079,7 +1233,7 @@ PVRSRVMapDeviceClassMemoryBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* get the device memory context */
        psMapDevClassMemOUT->eError =
                PVRSRVLookupHandle(psPerProc->psHandleBase,
                                   &hDevMemContextInt,
@@ -1091,7 +1245,7 @@ PVRSRVMapDeviceClassMemoryBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* Having looked up the handle, now check its type */
        switch(eHandleType)
        {
 #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)
@@ -1158,7 +1312,7 @@ PVRSRVMapDeviceClassMemoryBW(IMG_UINT32 ui32BridgeID,
 
        psMapDevClassMemOUT->sClientSyncInfo.hKernelSyncInfo = IMG_NULL;
 
-       
+       /* and setup the sync info */
        if(psMemInfo->psKernelSyncInfo)
        {
 #if !defined(PVRSRV_DISABLE_UM_SYNCOBJ_MAPPINGS)
@@ -1168,6 +1322,8 @@ PVRSRVMapDeviceClassMemoryBW(IMG_UINT32 ui32BridgeID,
                        psMemInfo->psKernelSyncInfo->sWriteOpsCompleteDevVAddr;
                psMapDevClassMemOUT->sClientSyncInfo.sReadOpsCompleteDevVAddr =
                        psMemInfo->psKernelSyncInfo->sReadOpsCompleteDevVAddr;
+               psMapDevClassMemOUT->sClientSyncInfo.sReadOps2CompleteDevVAddr =
+                       psMemInfo->psKernelSyncInfo->sReadOps2CompleteDevVAddr;
 
 #if defined (SUPPORT_SID_INTERFACE)
                if (psMemInfo->psKernelSyncInfo->psSyncDataMemInfoKM->sMemBlk.hOSMemHandle != 0)
@@ -1190,7 +1346,12 @@ PVRSRVMapDeviceClassMemoryBW(IMG_UINT32 ui32BridgeID,
 #endif
 
                psMapDevClassMemOUT->sClientMemInfo.psClientSyncInfo = &psMapDevClassMemOUT->sClientSyncInfo;
-               
+               /*
+                * The sync info is associated with the device buffer,
+                * and not allocated here.  It isn't exported when
+                * created, hence the handle allocation rather than a
+                * lookup.
+                */
                PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
                                                  &psMapDevClassMemOUT->sClientSyncInfo.hKernelSyncInfo,
                                                  psMemInfo->psKernelSyncInfo,
@@ -1253,7 +1414,7 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
                                          PVRSRV_BRIDGE_IN_WRAP_EXT_MEMORY *psWrapExtMemIN,
                                          PVRSRV_BRIDGE_OUT_WRAP_EXT_MEMORY *psWrapExtMemOUT,
                                          PVRSRV_PER_PROCESS_DATA *psPerProc);
-#else 
+#else /* OS_PVRSRV_WRAP_EXT_MEM_BW */
 static IMG_INT
 PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
                                          PVRSRV_BRIDGE_IN_WRAP_EXT_MEMORY *psWrapExtMemIN,
@@ -1270,7 +1431,10 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
 
        NEW_HANDLE_BATCH_OR_ERROR(psWrapExtMemOUT->eError, psPerProc, 2)
 
-       
+       /*
+        * FIXME: This needs reworking - don't use the user supplied page
+        * table list, get the list from the OS.
+        */
        psWrapExtMemOUT->eError =
                PVRSRVLookupHandle(psPerProc->psHandleBase, &hDevCookieInt,
                                                   psWrapExtMemIN->hDevCookie,
@@ -1280,7 +1444,7 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* get the device memory context */
        psWrapExtMemOUT->eError =
        PVRSRVLookupHandle(psPerProc->psHandleBase, &hDevMemContextInt,
                                   psWrapExtMemIN->hDevMemContext,
@@ -1309,7 +1473,7 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
                                                           ui32PageTableSize) != PVRSRV_OK)
                {
                        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,      ui32PageTableSize, (IMG_VOID *)psSysPAddr, 0);
-                       
+                       /*not nulling pointer, out of scope*/
                        return -EFAULT;
                }
        }
@@ -1331,7 +1495,7 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
                          ui32PageTableSize,
                          (IMG_VOID *)psSysPAddr, 0);
-               
+               /*not nulling pointer, out of scope*/
        }
 
        if(psWrapExtMemOUT->eError != PVRSRV_OK)
@@ -1342,12 +1506,13 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
        psWrapExtMemOUT->sClientMemInfo.pvLinAddrKM =
                        psMemInfo->pvLinAddrKM;
 
-       
+       /* setup the mem info */
        psWrapExtMemOUT->sClientMemInfo.pvLinAddr = 0;
        psWrapExtMemOUT->sClientMemInfo.sDevVAddr = psMemInfo->sDevVAddr;
        psWrapExtMemOUT->sClientMemInfo.ui32Flags = psMemInfo->ui32Flags;
     psWrapExtMemOUT->sClientMemInfo.uAllocSize = psMemInfo->uAllocSize;
 #if defined (SUPPORT_SID_INTERFACE)
+/* see below */
 #else
        psWrapExtMemOUT->sClientMemInfo.hMappingInfo = psMemInfo->sMemBlk.hOSMemHandle;
 #endif
@@ -1359,7 +1524,7 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
                                          PVRSRV_HANDLE_ALLOC_FLAG_NONE);
 
 #if defined (SUPPORT_SID_INTERFACE)
-       
+       /* alloc subhandle for the mapping info */
        if (psMemInfo->sMemBlk.hOSMemHandle != IMG_NULL)
        {
                PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
@@ -1375,7 +1540,7 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
        }
 #endif
 
-       
+       /* setup the sync info */
 #if !defined(PVRSRV_DISABLE_UM_SYNCOBJ_MAPPINGS)
        psWrapExtMemOUT->sClientSyncInfo.psSyncData =
                psMemInfo->psKernelSyncInfo->psSyncData;
@@ -1383,9 +1548,11 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
                psMemInfo->psKernelSyncInfo->sWriteOpsCompleteDevVAddr;
        psWrapExtMemOUT->sClientSyncInfo.sReadOpsCompleteDevVAddr =
                psMemInfo->psKernelSyncInfo->sReadOpsCompleteDevVAddr;
+       psWrapExtMemOUT->sClientSyncInfo.sReadOps2CompleteDevVAddr =
+               psMemInfo->psKernelSyncInfo->sReadOps2CompleteDevVAddr;
 
 #if defined (SUPPORT_SID_INTERFACE)
-       
+       /* alloc subhandle for the mapping info */
        if (psMemInfo->psKernelSyncInfo->psSyncDataMemInfoKM->sMemBlk.hOSMemHandle != IMG_NULL)
        {
                PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
@@ -1418,7 +1585,7 @@ PVRSRVWrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
 
        return 0;
 }
-#endif 
+#endif /* OS_PVRSRV_WRAP_EXT_MEM_BW */
 
 static IMG_INT
 PVRSRVUnwrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
@@ -1455,6 +1622,169 @@ PVRSRVUnwrapExtMemoryBW(IMG_UINT32 ui32BridgeID,
        return 0;
 }
 
+#if defined(SUPPORT_ION)
+static IMG_INT
+PVRSRVMapIonHandleBW(IMG_UINT32 ui32BridgeID,
+                                          PVRSRV_BRIDGE_IN_MAP_ION_HANDLE *psMapIonIN,
+                                          PVRSRV_BRIDGE_OUT_MAP_ION_HANDLE *psMapIonOUT,
+                                          PVRSRV_PER_PROCESS_DATA *psPerProc)
+{
+       PVRSRV_KERNEL_MEM_INFO  *psKernelMemInfo;
+
+       psMapIonOUT->eError = PVRSRVLookupHandle(psPerProc->psHandleBase,
+                                                                                        &psMapIonIN->hDevCookie,
+                                                                                        psMapIonIN->hDevCookie,
+                                                                                        PVRSRV_HANDLE_TYPE_DEV_NODE);
+       if (psMapIonOUT->eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: Failed to lookup device node handle", __FUNCTION__));
+               return 0;
+       }
+
+       psMapIonOUT->eError = PVRSRVLookupHandle(psPerProc->psHandleBase,
+                                                                                        &psMapIonIN->hDevMemContext,
+                                                                                        psMapIonIN->hDevMemContext,
+                                                                                        PVRSRV_HANDLE_TYPE_DEV_MEM_CONTEXT);
+       if (psMapIonOUT->eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: Failed to lookup memory context handle", __FUNCTION__));
+               return 0;
+       }
+
+       psMapIonOUT->eError = PVRSRVMapIonHandleKM(psPerProc,
+                                                                                          psMapIonIN->hDevCookie,
+                                                                                          psMapIonIN->hDevMemContext,
+                                                                                          psMapIonIN->handle,
+                                                                                          psMapIonIN->ui32Attribs,
+                                                                                          psMapIonIN->ui32Size,
+                                                                                          &psKernelMemInfo);
+       if (psMapIonOUT->eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: Failed to map ion handle", __FUNCTION__));
+               return 0;
+       }
+
+       OSMemSet(&psMapIonOUT->sClientMemInfo,
+                        0,
+                        sizeof(psMapIonOUT->sClientMemInfo));
+
+       psMapIonOUT->sClientMemInfo.pvLinAddrKM =
+                       psKernelMemInfo->pvLinAddrKM;
+
+       psMapIonOUT->sClientMemInfo.pvLinAddr = 0;
+       psMapIonOUT->sClientMemInfo.sDevVAddr = psKernelMemInfo->sDevVAddr;
+       psMapIonOUT->sClientMemInfo.ui32Flags = psKernelMemInfo->ui32Flags;
+       psMapIonOUT->sClientMemInfo.uAllocSize = psKernelMemInfo->uAllocSize;
+
+       /* No mapping info, we map through ion */
+       psMapIonOUT->sClientMemInfo.hMappingInfo = IMG_NULL;
+
+
+       PVRSRVAllocHandleNR(psPerProc->psHandleBase,
+                                               &psMapIonOUT->sClientMemInfo.hKernelMemInfo,
+                                               psKernelMemInfo,
+                                               PVRSRV_HANDLE_TYPE_MEM_INFO,
+                                               PVRSRV_HANDLE_ALLOC_FLAG_NONE);
+
+       if(psMapIonIN->ui32Attribs & PVRSRV_MEM_NO_SYNCOBJ)
+       {
+               /* signal no syncinfo */
+               OSMemSet(&psMapIonOUT->sClientSyncInfo,
+                                0,
+                                sizeof (PVRSRV_CLIENT_SYNC_INFO));
+               psMapIonOUT->sClientMemInfo.psClientSyncInfo = IMG_NULL;
+       }
+       else
+       {
+               /* and setup the sync info */
+#if !defined(PVRSRV_DISABLE_UM_SYNCOBJ_MAPPINGS)
+               psMapIonOUT->sClientSyncInfo.psSyncData =
+                       psKernelMemInfo->psKernelSyncInfo->psSyncData;
+               psMapIonOUT->sClientSyncInfo.sWriteOpsCompleteDevVAddr =
+                       psKernelMemInfo->psKernelSyncInfo->sWriteOpsCompleteDevVAddr;
+               psMapIonOUT->sClientSyncInfo.sReadOpsCompleteDevVAddr =
+                       psKernelMemInfo->psKernelSyncInfo->sReadOpsCompleteDevVAddr;
+               psMapIonOUT->sClientSyncInfo.sReadOps2CompleteDevVAddr =
+                       psKernelMemInfo->psKernelSyncInfo->sReadOps2CompleteDevVAddr;
+
+#if defined (SUPPORT_SID_INTERFACE)
+               if (psKernelMemInfo->psKernelSyncInfo->psSyncDataMemInfoKM->sMemBlk.hOSMemHandle != IMG_NULL)
+               {
+                               PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
+                                                                          &psMapIonOUT->sClientSyncInfo.hMappingInfo,
+                                                                          psMemInfo->psKernelSyncInfo->psSyncDataMemInfoKM->sMemBlk.hOSMemHandle,
+                                                                          PVRSRV_HANDLE_TYPE_SYNC_INFO,
+                                                                          PVRSRV_HANDLE_ALLOC_FLAG_NONE,
+                                                                          psMapIonOUT->sClientMemInfo.hKernelMemInfo);
+               }
+               else
+               {
+                       psMapIonOUT->sClientSyncInfo.hMappingInfo = 0;
+               }
+#else
+               psMapIonOUT->sClientSyncInfo.hMappingInfo =
+                       psKernelMemInfo->psKernelSyncInfo->psSyncDataMemInfoKM->sMemBlk.hOSMemHandle;
+#endif
+#endif
+
+               PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
+                                                          &psMapIonOUT->sClientSyncInfo.hKernelSyncInfo,
+                                                          psKernelMemInfo->psKernelSyncInfo,
+                                                          PVRSRV_HANDLE_TYPE_SYNC_INFO,
+                                                          PVRSRV_HANDLE_ALLOC_FLAG_NONE,
+                                                          psMapIonOUT->sClientMemInfo.hKernelMemInfo);
+
+               psMapIonOUT->sClientMemInfo.psClientSyncInfo =
+                       &psMapIonOUT->sClientSyncInfo;
+       }
+       return 0;
+}
+
+static IMG_INT
+PVRSRVUnmapIonHandleBW(IMG_UINT32 ui32BridgeID,
+                                          PVRSRV_BRIDGE_IN_UNMAP_ION_HANDLE *psUnmapIonIN,
+                                          PVRSRV_BRIDGE_RETURN *psUnmapIonOUT,
+                                          PVRSRV_PER_PROCESS_DATA *psPerProc)
+{
+       IMG_VOID *pvKernelMemInfo;
+
+       PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_UNMAP_ION_HANDLE);
+
+       psUnmapIonOUT->eError =
+        PVRSRVLookupHandle(psPerProc->psHandleBase,
+                           &pvKernelMemInfo,
+#if defined (SUPPORT_SID_INTERFACE)
+                                                  psUnmapIonIN->hKernelMemInfo,
+#else
+                                                  psUnmapIonIN->psKernelMemInfo,
+#endif
+                                                  PVRSRV_HANDLE_TYPE_MEM_INFO);
+
+       if(psUnmapIonOUT->eError != PVRSRV_OK)
+       {
+               return 0;
+       }
+
+       psUnmapIonOUT->eError = PVRSRVUnmapIonHandleKM(pvKernelMemInfo);
+
+       if(psUnmapIonOUT->eError != PVRSRV_OK)
+       {
+               return 0;
+       }
+
+       psUnmapIonOUT->eError =
+               PVRSRVReleaseHandle(psPerProc->psHandleBase,
+#if defined (SUPPORT_SID_INTERFACE)
+                                                       psUnmapIonIN->hKernelMemInfo,
+#else
+                                                       psUnmapIonIN->psKernelMemInfo,
+#endif
+                                                       PVRSRV_HANDLE_TYPE_MEM_INFO);
+
+       return 0;
+}
+#endif /* SUPPORT_ION */
+
 static IMG_INT
 PVRSRVGetFreeDeviceMemBW(IMG_UINT32 ui32BridgeID,
                                                 PVRSRV_BRIDGE_IN_GETFREEDEVICEMEM *psGetFreeDeviceMemIN,
@@ -1482,7 +1812,7 @@ PVRMMapOSMemHandleToMMapDataBW(IMG_UINT32 ui32BridgeID,
 {
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_MHANDLE_TO_MMAP_DATA);
 
-#if defined (__linux__) || defined(__QNXNTO__)
+#if defined (__linux__) || defined (__QNXNTO__)
        psMMapDataOUT->eError =
                PVRMMapOSMemHandleToMMapData(psPerProc,
                                                                                psMMapDataIN->hMHandle,
@@ -1508,7 +1838,7 @@ PVRMMapReleaseMMapDataBW(IMG_UINT32 ui32BridgeID,
 {
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_RELEASE_MMAP_DATA);
 
-#if defined (__linux__) || defined(__QNXNTO__)
+#if defined (__linux__) || defined (__QNXNTO__)
        psMMapDataOUT->eError =
                PVRMMapReleaseMMapData(psPerProc,
                                                                                psMMapDataIN->hMHandle,
@@ -1938,7 +2268,7 @@ PDumpSyncPolBW(IMG_UINT32 ui32BridgeID,
                ui32Offset = offsetof(PVRSRV_SYNC_DATA, ui32WriteOpsComplete);
        }
 
-       
+       /* FIXME:  Move this code to somewhere outside of the bridge */
        if (psPDumpSyncPolIN->bUseLastOpDumpVal)
        {
                if(psPDumpSyncPolIN->bIsRead)
@@ -2057,7 +2387,7 @@ PDumpStopInitPhaseBW(IMG_UINT32 ui32BridgeID,
        return 0;
 }
 
-#endif 
+#endif /* PDUMP */
 
 
 static IMG_INT
@@ -2072,6 +2402,7 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
        PVRSRV_ERROR eError;
 
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_GET_MISC_INFO);
+
 #if defined (SUPPORT_SID_INTERFACE)
        sMiscInfo.ui32StateRequest = psGetMiscInfoIN->sMiscInfo.ui32StateRequest;
        sMiscInfo.ui32StatePresent = psGetMiscInfoIN->sMiscInfo.ui32StatePresent;
@@ -2081,8 +2412,10 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
        OSMemCopy(&sMiscInfo.sCacheOpCtl,
                          &psGetMiscInfoIN->sMiscInfo.sCacheOpCtl,
                          sizeof(sMiscInfo.sCacheOpCtl));
+       OSMemCopy(&sMiscInfo.sGetRefCountCtl,
+                         &psGetMiscInfoIN->sMiscInfo.sGetRefCountCtl,
+                         sizeof(sMiscInfo.sGetRefCountCtl));
 #else
-
        OSMemCopy(&psGetMiscInfoOUT->sMiscInfo,
                          &psGetMiscInfoIN->sMiscInfo,
                          sizeof(PVRSRV_MISC_INFO));
@@ -2092,7 +2425,8 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
            ((psGetMiscInfoIN->sMiscInfo.ui32StateRequest & PVRSRV_MISC_INFO_DDKVERSION_PRESENT) != 0) &&
            ((psGetMiscInfoIN->sMiscInfo.ui32StateRequest & PVRSRV_MISC_INFO_FREEMEM_PRESENT) != 0))
        {
-               
+               /* Client must choose which of memstats and DDK version will be written to
+                * kernel side buffer */
                psGetMiscInfoOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
                return 0;
        }
@@ -2101,7 +2435,7 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
            ((psGetMiscInfoIN->sMiscInfo.ui32StateRequest & PVRSRV_MISC_INFO_DDKVERSION_PRESENT) != 0) ||
            ((psGetMiscInfoIN->sMiscInfo.ui32StateRequest & PVRSRV_MISC_INFO_FREEMEM_PRESENT) != 0))
        {
-               
+               /* Alloc kernel side buffer to write into */
 #if defined (SUPPORT_SID_INTERFACE)
                ASSIGN_AND_EXIT_ON_ERROR(psGetMiscInfoOUT->eError,
                                        OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
@@ -2110,7 +2444,7 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
                                                        "Output string buffer"));
                psGetMiscInfoOUT->eError = PVRSRVGetMiscInfoKM(&sMiscInfo);
 
-               
+               /* Copy result to user */
                eError = CopyToUserWrapper(psPerProc, ui32BridgeID,
                                                                        psGetMiscInfoIN->sMiscInfo.pszMemoryStr,
                                                                        sMiscInfo.pszMemoryStr,
@@ -2124,14 +2458,14 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
 
                psGetMiscInfoOUT->eError = PVRSRVGetMiscInfoKM(&psGetMiscInfoOUT->sMiscInfo);
 
-               
+               /* Copy result to user */
                eError = CopyToUserWrapper(psPerProc, ui32BridgeID,
                                           psGetMiscInfoIN->sMiscInfo.pszMemoryStr,
                                           psGetMiscInfoOUT->sMiscInfo.pszMemoryStr,
                                           psGetMiscInfoOUT->sMiscInfo.ui32MemoryStrLen);
 #endif
 
-               
+               /* Free kernel side buffer again */
 #if defined (SUPPORT_SID_INTERFACE)
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
                                        sMiscInfo.ui32MemoryStrLen,
@@ -2142,12 +2476,16 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
                         (IMG_VOID *)psGetMiscInfoOUT->sMiscInfo.pszMemoryStr, 0);
 #endif
 
-               
+               /* Replace output buffer pointer with input pointer, as both are expected
+                * to point to the same userspace memory.
+                */
                psGetMiscInfoOUT->sMiscInfo.pszMemoryStr = psGetMiscInfoIN->sMiscInfo.pszMemoryStr;
 
                if(eError != PVRSRV_OK)
                {
-                       
+                       /* Do error check at the end as we always have to free and reset the
+                        * pointer.
+                        */
                        PVR_DPF((PVR_DBG_ERROR, "PVRSRVGetMiscInfoBW Error copy to user"));
                        return -EFAULT;
                }
@@ -2161,13 +2499,19 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
 #endif
        }
 
-       
+       /* Return on error so exit status of PVRSRVGetMiscInfoKM is propagated to client.
+        * Don't alloc handles for event object or timer; if error exit status is returned
+        * the handles should not be used (even if not null) */
        if (psGetMiscInfoOUT->eError != PVRSRV_OK)
        {
                return 0;
        }
 
-       
+       /*
+        * The handles are not allocated in batch mode as they are shared
+        * (a shared handle is allocated at most once), and there is no
+        * resource allocation to undo if the handle allocation fails.
+        */
 #if defined (SUPPORT_SID_INTERFACE)
        if (sMiscInfo.ui32StateRequest & PVRSRV_MISC_INFO_GLOBALEVENTOBJECT_PRESENT)
 #else
@@ -2193,7 +2537,6 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
                OSMemCopy(&psGetMiscInfoOUT->sMiscInfo.sGlobalEventObject.szName,
                                                        sMiscInfo.sGlobalEventObject.szName,
                                                        EVENTOBJNAME_MAXLENGTH);
-
 #endif
        }
 
@@ -2203,7 +2546,7 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
        if (psGetMiscInfoOUT->sMiscInfo.hSOCTimerRegisterOSMemHandle)
 #endif
        {
-               
+               /* Allocate handle for SOC OSMemHandle */
                psGetMiscInfoOUT->eError = PVRSRVAllocHandle(psPerProc->psHandleBase,
                                                  &psGetMiscInfoOUT->sMiscInfo.hSOCTimerRegisterOSMemHandle,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -2225,7 +2568,7 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
                psGetMiscInfoOUT->sMiscInfo.hSOCTimerRegisterOSMemHandle = 0;
        }
 
-       
+       /* copy data from local sMiscInfo to OUT */
        psGetMiscInfoOUT->sMiscInfo.ui32StateRequest = sMiscInfo.ui32StateRequest;
        psGetMiscInfoOUT->sMiscInfo.ui32StatePresent = sMiscInfo.ui32StatePresent;
 
@@ -2241,6 +2584,9 @@ PVRSRVGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
        OSMemCopy(&psGetMiscInfoOUT->sMiscInfo.sCacheOpCtl,
                                &sMiscInfo.sCacheOpCtl,
                                sizeof(psGetMiscInfoOUT->sMiscInfo.sCacheOpCtl));
+       OSMemCopy(&psGetMiscInfoOUT->sMiscInfo.sGetRefCountCtl,
+                               &sMiscInfo.sGetRefCountCtl,
+                               sizeof(psGetMiscInfoOUT->sMiscInfo.sGetRefCountCtl));
 #endif
 
        return 0;
@@ -2255,19 +2601,27 @@ PVRSRVConnectBW(IMG_UINT32 ui32BridgeID,
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_CONNECT_SERVICES);
 
 #if defined(PDUMP)
-       
+       /* Store the per process connection info.
+        * The Xserver initially connects via PVR2D which sets the persistent flag.
+        * But, later the Xserver may connect via SGL which doesn't carry the flag (in
+        * general SGL clients aren't persistent). So we OR in the flag so if it was set
+        * before it remains set.
+        */
        if ((psConnectServicesIN->ui32Flags & SRV_FLAGS_PERSIST) != 0)
        {
        psPerProc->bPDumpPersistent = IMG_TRUE;
        }
 
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-       
+       /* Select whether this client is our 'active' target for pdumping in a
+        * multi-process environment.
+        * NOTE: only 1 active target is supported at present.
+        */
        if ((psConnectServicesIN->ui32Flags & SRV_FLAGS_PDUMP_ACTIVE) != 0)
        {
        psPerProc->bPDumpActive = IMG_TRUE;
        }
-#endif 
+#endif /* SUPPORT_PDUMP_MULTI_PROCESS */
 #else
        PVR_UNREFERENCED_PARAMETER(psConnectServicesIN);
 #endif
@@ -2288,7 +2642,7 @@ PVRSRVDisconnectBW(IMG_UINT32 ui32BridgeID,
 
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_DISCONNECT_SERVICES);
 
-       
+       /* just return OK, per-process data is cleaned up by resmgr */
        psRetOUT->eError = PVRSRV_OK;
 
        return 0;
@@ -2377,7 +2731,7 @@ PVRSRVCloseDCDeviceBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       psRetOUT->eError = PVRSRVCloseDCDeviceKM(pvDispClassInfoInt, IMG_FALSE);
+       psRetOUT->eError = PVRSRVCloseDCDeviceKM(pvDispClassInfoInt);
        if(psRetOUT->eError != PVRSRV_OK)
        {
                return 0;
@@ -2448,9 +2802,10 @@ PVRSRVEnumDCDimsBW(IMG_UINT32 ui32BridgeID,
        return 0;
 }
 
+#if defined(SUPPORT_PVRSRV_GET_DC_SYSTEM_BUFFER)
 static IMG_INT
 PVRSRVGetDCSystemBufferBW(IMG_UINT32 ui32BridgeID,
-                                                 PVRSRV_BRIDGE_IN_GET_DISPCLASS_SYSBUFFER *psGetDispClassSysBufferIN,  
+                                                 PVRSRV_BRIDGE_IN_GET_DISPCLASS_SYSBUFFER *psGetDispClassSysBufferIN,  //IMG_HANDLE *phGetDispClassSysBufferIN,
                                                  PVRSRV_BRIDGE_OUT_GET_DISPCLASS_SYSBUFFER *psGetDispClassSysBufferOUT,
                                                  PVRSRV_PER_PROCESS_DATA *psPerProc)
 {
@@ -2480,7 +2835,7 @@ PVRSRVGetDCSystemBufferBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-        
+       /* PRQA S 1461 6 */ /* ignore warning about enum type being converted */
        PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
                                                 &psGetDispClassSysBufferOUT->hBuffer,
                                                 hBufferInt,
@@ -2492,6 +2847,7 @@ PVRSRVGetDCSystemBufferBW(IMG_UINT32 ui32BridgeID,
 
        return 0;
 }
+#endif
 
 static IMG_INT
 PVRSRVGetDCInfoBW(IMG_UINT32 ui32BridgeID,
@@ -2545,7 +2901,7 @@ PVRSRVCreateDCSwapChainBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* Get ui32SwapChainID from input */
        ui32SwapChainID = psCreateDispClassSwapChainIN->ui32SwapChainID;
 
        psCreateDispClassSwapChainOUT->eError =
@@ -2563,7 +2919,7 @@ PVRSRVCreateDCSwapChainBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* Pass ui32SwapChainID to output */
        psCreateDispClassSwapChainOUT->ui32SwapChainID = ui32SwapChainID;
 
        PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
@@ -2824,10 +3180,11 @@ PVRSRVGetDCBuffersBW(IMG_UINT32 ui32BridgeID,
                                                         pvSwapChain,
                                                         &psGetDispClassBuffersOUT->ui32BufferCount,
 #if defined (SUPPORT_SID_INTERFACE)
-                             pahBuffer);
+                                                        pahBuffer,
 #else
-                             psGetDispClassBuffersOUT->ahBuffer);
+                                                        psGetDispClassBuffersOUT->ahBuffer,
 #endif
+                                                        psGetDispClassBuffersOUT->asPhyAddr);
        if (psGetDispClassBuffersOUT->eError != PVRSRV_OK)
        {
                return 0;
@@ -2843,7 +3200,7 @@ PVRSRVGetDCBuffersBW(IMG_UINT32 ui32BridgeID,
                IMG_HANDLE hBufferExt;
 #endif
 
-        
+       /* PRQA S 1461 15 */ /* ignore warning about enum type being converted */
 #if defined (SUPPORT_SID_INTERFACE)
        PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
                                                        &hBufferExt,
@@ -2929,7 +3286,6 @@ PVRSRVSwapToDCBufferBW(IMG_UINT32 ui32BridgeID,
        }
 #endif
 
-
        psRetOUT->eError =
                PVRSRVSwapToDCBufferKM(pvDispClassInfo,
                                                           pvSwapChainBuf,
@@ -2945,6 +3301,136 @@ PVRSRVSwapToDCBufferBW(IMG_UINT32 ui32BridgeID,
        return 0;
 }
 
+static IMG_INT
+PVRSRVSwapToDCBuffer2BW(IMG_UINT32 ui32BridgeID,
+                                               PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_BUFFER2 *psSwapDispClassBufferIN,
+                                               PVRSRV_BRIDGE_RETURN *psRetOUT,
+                                               PVRSRV_PER_PROCESS_DATA *psPerProc)
+{
+       IMG_VOID *pvPrivData = IMG_NULL;
+       IMG_VOID *pvDispClassInfo;
+       IMG_VOID *pvSwapChain;
+       IMG_UINT32 i;
+
+       PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_SWAP_DISPCLASS_TO_BUFFER2);
+
+       psRetOUT->eError =
+               PVRSRVLookupHandle(psPerProc->psHandleBase,
+                                                  &pvDispClassInfo,
+                                                  psSwapDispClassBufferIN->hDeviceKM,
+                                                  PVRSRV_HANDLE_TYPE_DISP_INFO);
+       if(psRetOUT->eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "PVRSRVSwapToDCBuffer2BW: Failed to look up DISP_INFO handle"));
+               return 0;
+       }
+
+       psRetOUT->eError =
+               PVRSRVLookupSubHandle(psPerProc->psHandleBase,
+                                                         &pvSwapChain,
+                                                         psSwapDispClassBufferIN->hSwapChain,
+                                                         PVRSRV_HANDLE_TYPE_DISP_SWAP_CHAIN,
+                                                         psSwapDispClassBufferIN->hDeviceKM);
+       if(psRetOUT->eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "PVRSRVSwapToDCBuffer2BW: Failed to look up DISP_BUFFER handle"));
+               return 0;
+       }
+
+       if(!OSAccessOK(PVR_VERIFY_WRITE,
+                                  psSwapDispClassBufferIN->ppsKernelMemInfos,
+                                  sizeof(IMG_HANDLE) * psSwapDispClassBufferIN->ui32NumMemInfos))
+       {
+               PVR_DPF((PVR_DBG_ERROR, "PVRSRVSwapToDCBuffer2BW: Access check failed for ppsKernelMemInfos"));
+               return -EFAULT;
+       }
+
+       if(!OSAccessOK(PVR_VERIFY_WRITE,
+                                  psSwapDispClassBufferIN->ppsKernelSyncInfos,
+                                  sizeof(IMG_HANDLE) * psSwapDispClassBufferIN->ui32NumMemInfos))
+       {
+               PVR_DPF((PVR_DBG_ERROR, "PVRSRVSwapToDCBuffer2BW: Access check failed for ppsKernelSyncInfos"));
+               return -EFAULT;
+       }
+
+       for (i = 0; i < psSwapDispClassBufferIN->ui32NumMemInfos; i++)
+       {
+               PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo;
+               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo;
+
+               psRetOUT->eError =
+                       PVRSRVLookupHandle(psPerProc->psHandleBase,
+                                                          (IMG_PVOID *)&psKernelMemInfo,
+                                                          psSwapDispClassBufferIN->ppsKernelMemInfos[i],
+                                                          PVRSRV_HANDLE_TYPE_MEM_INFO);
+               if(psRetOUT->eError != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVSwapToDCBuffer2BW: Failed to look up MEM_INFO handle"));
+                       return 0;
+               }
+
+               psRetOUT->eError =
+                       PVRSRVLookupHandle(psPerProc->psHandleBase,
+                                                          (IMG_PVOID *)&psKernelSyncInfo,
+                                                          psSwapDispClassBufferIN->ppsKernelSyncInfos[i],
+                                                          PVRSRV_HANDLE_TYPE_SYNC_INFO);
+               if(psRetOUT->eError != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVSwapToDCBuffer2BW: Failed to look up SYNC_INFO handle"));
+                       return 0;
+               }
+
+               psSwapDispClassBufferIN->ppsKernelMemInfos[i] = psKernelMemInfo;
+               psSwapDispClassBufferIN->ppsKernelSyncInfos[i] = psKernelSyncInfo;
+       }
+
+       if(psSwapDispClassBufferIN->ui32PrivDataLength > 0)
+       {
+               if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                         psSwapDispClassBufferIN->ui32PrivDataLength,
+                                         (IMG_VOID **)&pvPrivData, IMG_NULL,
+                                         "Swap Command Private Data") != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2BW: Failed to allocate private data space"));
+                       return -ENOMEM;
+               }
+
+               if(CopyFromUserWrapper(psPerProc,
+                                                          ui32BridgeID,
+                                                          pvPrivData,
+                                                          psSwapDispClassBufferIN->pvPrivData,
+                                                          psSwapDispClassBufferIN->ui32PrivDataLength) != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVSwapToDCBuffer2BW: Failed to copy private data"));
+                       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                         psSwapDispClassBufferIN->ui32PrivDataLength,
+                                         pvPrivData, IMG_NULL);
+               return -EFAULT;
+               }
+       }
+
+       psRetOUT->eError =
+               PVRSRVSwapToDCBuffer2KM(pvDispClassInfo,
+                                                               pvSwapChain,
+                                                               psSwapDispClassBufferIN->ui32SwapInterval,
+                                                               psSwapDispClassBufferIN->ppsKernelMemInfos,
+                                                               psSwapDispClassBufferIN->ppsKernelSyncInfos,
+                                                               psSwapDispClassBufferIN->ui32NumMemInfos,
+                                                               pvPrivData,
+                                                               psSwapDispClassBufferIN->ui32PrivDataLength);
+
+       if(psRetOUT->eError != PVRSRV_OK)
+       {
+               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                 psSwapDispClassBufferIN->ui32PrivDataLength,
+                                 pvPrivData, IMG_NULL);
+       }
+
+    return 0;
+}
+
+
+
 static IMG_INT
 PVRSRVSwapToDCSystemBW(IMG_UINT32 ui32BridgeID,
                                           PVRSRV_BRIDGE_IN_SWAP_DISPCLASS_TO_SYSTEM *psSwapDispClassSystemIN,
@@ -3048,7 +3534,7 @@ PVRSRVCloseBCDeviceBW(IMG_UINT32 ui32BridgeID,
        }
 
        psRetOUT->eError =
-               PVRSRVCloseBCDeviceKM(pvBufClassInfo, IMG_FALSE);
+               PVRSRVCloseBCDeviceKM(pvBufClassInfo);
 
        if(psRetOUT->eError != PVRSRV_OK)
        {
@@ -3121,7 +3607,7 @@ PVRSRVGetBCBufferBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-        
+       /* PRQA S 1461 6 */ /* ignore warning about enum type being converted */
        PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
                                                 &psGetBufferClassBufferOUT->hBuffer,
                                                 hBufferInt,
@@ -3291,7 +3777,11 @@ PVRSRVMapMemInfoMemBW(IMG_UINT32 ui32BridgeID,
                        return 0;
        }
 
-       
+       /*
+        * To prevent the building up of deep chains of subhandles, parent
+        * the new meminfo off the parent of the input meminfo, if it has
+        * a parent.
+        */
        psMapMemInfoMemOUT->eError =
                PVRSRVGetParentHandle(psPerProc->psHandleBase,
                                        &hParent,
@@ -3351,14 +3841,14 @@ PVRSRVMapMemInfoMemBW(IMG_UINT32 ui32BridgeID,
 
        if(psKernelMemInfo->ui32Flags & PVRSRV_MEM_NO_SYNCOBJ)
        {
-               
+               /* signal no syncinfo */
                OSMemSet(&psMapMemInfoMemOUT->sClientSyncInfo,
                                 0,
                                 sizeof (PVRSRV_CLIENT_SYNC_INFO));
        }
        else
        {
-               
+               /* and setup the sync info */
 #if !defined(PVRSRV_DISABLE_UM_SYNCOBJ_MAPPINGS)
                psMapMemInfoMemOUT->sClientSyncInfo.psSyncData =
                        psKernelMemInfo->psKernelSyncInfo->psSyncData;
@@ -3366,6 +3856,8 @@ PVRSRVMapMemInfoMemBW(IMG_UINT32 ui32BridgeID,
                        psKernelMemInfo->psKernelSyncInfo->sWriteOpsCompleteDevVAddr;
                psMapMemInfoMemOUT->sClientSyncInfo.sReadOpsCompleteDevVAddr =
                        psKernelMemInfo->psKernelSyncInfo->sReadOpsCompleteDevVAddr;
+               psMapMemInfoMemOUT->sClientSyncInfo.sReadOps2CompleteDevVAddr =
+                       psKernelMemInfo->psKernelSyncInfo->sReadOps2CompleteDevVAddr;
 
 #if defined (SUPPORT_SID_INTERFACE)
        if (psKernelMemInfo->psKernelSyncInfo->psSyncDataMemInfoKM->sMemBlk.hOSMemHandle != IMG_NULL)
@@ -3430,13 +3922,25 @@ DummyBW(IMG_UINT32 ui32BridgeID,
 }
 
 
+/*!
+ * *****************************************************************************
+ * @brief A wrapper for filling in the g_BridgeDispatchTable array that does
+ *               error checking.
+ *
+ * @param ui32Index
+ * @param pszIOCName
+ * @param pfFunction
+ * @param pszFunctionName
+ *
+ * @return
+ ********************************************************************************/
 IMG_VOID
 _SetDispatchTableEntry(IMG_UINT32 ui32Index,
                                           const IMG_CHAR *pszIOCName,
                                           BridgeWrapperFunction pfFunction,
                                           const IMG_CHAR *pszFunctionName)
 {
-       static IMG_UINT32 ui32PrevIndex = ~0UL;         
+       static IMG_UINT32 ui32PrevIndex = ~0UL;         /* -1 */
 #if !defined(DEBUG)
        PVR_UNREFERENCED_PARAMETER(pszIOCName);
 #endif
@@ -3445,11 +3949,16 @@ _SetDispatchTableEntry(IMG_UINT32 ui32Index,
 #endif
 
 #if defined(DEBUG_BRIDGE_KM_DISPATCH_TABLE)
-       
+       /* INTEGRATION_POINT: Enable this to dump out the dispatch table entries */
        PVR_DPF((PVR_DBG_WARNING, "%s: %d %s %s", __FUNCTION__, ui32Index, pszIOCName, pszFunctionName));
 #endif
 
-       
+       /* We should never be over-writing a previous entry.
+        * If we are, tell the world about it.
+        * NOTE: This shouldn't be debug only since switching from debug->release
+        * etc is likly to modify the available ioctls and thus be a point where
+        * mistakes are exposed. This isn't run at at a performance critical time.
+        */
        if(g_BridgeDispatchTable[ui32Index].pfFunction)
        {
 #if defined(DEBUG_BRIDGE_KM)
@@ -3464,7 +3973,17 @@ _SetDispatchTableEntry(IMG_UINT32 ui32Index,
                PVR_DPF((PVR_DBG_ERROR, "NOTE: Enabling DEBUG_BRIDGE_KM_DISPATCH_TABLE may help debug this issue."));
        }
 
-       
+       /* Any gaps are sub-optimal in-terms of memory usage, but we are mainly
+        * interested in spotting any large gap of wasted memory that could be
+        * accidentally introduced.
+        *
+        * This will currently flag up any gaps > 5 entries.
+        *
+        * NOTE: This shouldn't be debug only since switching from debug->release
+        * etc is likly to modify the available ioctls and thus be a point where
+        * mistakes are exposed. This isn't run at at a performance critical time.
+        */
+//     if((ui32PrevIndex != (IMG_UINT32)-1) &&
        if((ui32PrevIndex != ~0UL) &&
           ((ui32Index >= ui32PrevIndex + DISPATCH_TABLE_GAP_THRESHOLD) ||
                (ui32Index <= ui32PrevIndex)))
@@ -3504,14 +4023,14 @@ PVRSRVInitSrvConnectBW(IMG_UINT32 ui32BridgeID,
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_INITSRV_CONNECT);
        PVR_UNREFERENCED_PARAMETER(psBridgeIn);
 
-        
+       /* PRQA S 3415 1 */ /* side effects needed - if any step fails */
        if((OSProcHasPrivSrvInit() == IMG_FALSE) || PVRSRVGetInitServerState(PVRSRV_INIT_SERVER_RUNNING) || PVRSRVGetInitServerState(PVRSRV_INIT_SERVER_RAN))
        {
                psRetOUT->eError = PVRSRV_ERROR_SRV_CONNECT_FAILED;
                return 0;
        }
 
-#if defined (__linux__) || defined(__QNXNTO__)
+#if defined (__linux__) || defined (__QNXNTO__)
        PVRSRVSetInitServerState(PVRSRV_INIT_SERVER_RUNNING, IMG_TRUE);
 #endif
        psPerProc->bInitProcess = IMG_TRUE;
@@ -3538,6 +4057,10 @@ PVRSRVInitSrvDisconnectBW(IMG_UINT32 ui32BridgeID,
 
        psPerProc->bInitProcess = IMG_FALSE;
 
+#if defined(SUPPORT_PDUMP_MULTI_PROCESS)
+    psPerProc->bPDumpActive = IMG_FALSE;
+#endif
+
        PVRSRVSetInitServerState(PVRSRV_INIT_SERVER_RUNNING, IMG_FALSE);
        PVRSRVSetInitServerState(PVRSRV_INIT_SERVER_RAN, IMG_TRUE);
 
@@ -3623,6 +4146,8 @@ PVRSRVEventObjectOpenBW(IMG_UINT32 ui32BridgeID,
        }
 
 #if defined (SUPPORT_SID_INTERFACE)
+/* Windows7, WinXP and Vista already use an Index type handle which the client glue uses directly */
+/* Linux requires a SID handle */
 #if !defined (WINXP) && !defined(SUPPORT_VISTA)
        PVRSRVAllocHandleNR(psPerProc->psHandleBase,
                                                &psEventObjectOpenOUT->hOSEvent,
@@ -3687,7 +4212,7 @@ PVRSRVEventObjectCloseBW(IMG_UINT32 ui32BridgeID,
                                                        &psEventObjectCloseIN->sEventObject.szName,
                                                        EVENTOBJNAME_MAXLENGTH) != PVRSRV_OK)
        {
-               
+               /*not nulling pointer, out of scope*/
                return -EFAULT;
        }
 
@@ -3707,42 +4232,55 @@ typedef struct _MODIFY_SYNC_OP_INFO
        IMG_UINT32      ui32ModifyFlags;
        IMG_UINT32      ui32ReadOpsPendingSnapShot;
        IMG_UINT32      ui32WriteOpsPendingSnapShot;
+       IMG_UINT32      ui32ReadOps2PendingSnapShot;
 } MODIFY_SYNC_OP_INFO;
 
 
 static PVRSRV_ERROR DoQuerySyncOpsSatisfied(PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo,
                                                                                        IMG_UINT32 ui32ReadOpsPendingSnapShot,
-                                            IMG_UINT32 ui32WriteOpsPendingSnapShot)
+                                                                                       IMG_UINT32 ui32WriteOpsPendingSnapShot,
+                                                                                       IMG_UINT32 ui32ReadOps2PendingSnapShot)
 {
        IMG_UINT32 ui32WriteOpsPending;
        IMG_UINT32 ui32ReadOpsPending;
+       IMG_UINT32 ui32ReadOps2Pending;
+
+       /*
+        *
+        * We wait until the complete count reaches _or_moves_past_ the
+        * snapshot value.
+        *
+        */
 
-       
        if (!psKernelSyncInfo)
        {
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
-
-
-
-
-
-
-
+       /*
+        let p be the pending ops count
+        let c be the complete ops count
+        let p' be the previously taken snapshot
 
+        if p exceeds c by an amount greater than that by which
+        p exceeds p', then the condition is not yet satisfied.
 
+        Note that (p - c) can never be negative, and neither can (p - p')
+        so we can do the comparison using unsigned arithmetic
+       */
        ui32WriteOpsPending = psKernelSyncInfo->psSyncData->ui32WriteOpsPending;
        ui32ReadOpsPending = psKernelSyncInfo->psSyncData->ui32ReadOpsPending;
+       ui32ReadOps2Pending = psKernelSyncInfo->psSyncData->ui32ReadOps2Pending;
 
        if((ui32WriteOpsPending - ui32WriteOpsPendingSnapShot >=
                ui32WriteOpsPending - psKernelSyncInfo->psSyncData->ui32WriteOpsComplete) &&
           (ui32ReadOpsPending - ui32ReadOpsPendingSnapShot >=
-        ui32ReadOpsPending - psKernelSyncInfo->psSyncData->ui32ReadOpsComplete))
+               ui32ReadOpsPending - psKernelSyncInfo->psSyncData->ui32ReadOpsComplete) &&
+               (ui32ReadOps2Pending - ui32ReadOps2PendingSnapShot >=
+               ui32ReadOps2Pending - psKernelSyncInfo->psSyncData->ui32ReadOps2Complete))
        {
 #if defined(PDUMP) && !defined(SUPPORT_VGX)
-               
+               /* pdump the sync pol: reads */
                PDumpComment("Poll for read ops complete to reach value (pdump: %u, actual snapshot: %u)",
                                         psKernelSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                         ui32ReadOpsPendingSnapShot);
@@ -3750,11 +4288,11 @@ static PVRSRV_ERROR DoQuerySyncOpsSatisfied(PVRSRV_KERNEL_SYNC_INFO *psKernelSyn
                                          offsetof(PVRSRV_SYNC_DATA, ui32ReadOpsComplete),
                                          psKernelSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                          0xFFFFFFFF,
-                                         PDUMP_POLL_OPERATOR_EQUAL, 
+                                         PDUMP_POLL_OPERATOR_EQUAL, /*  * see "NB" below */
                                          0,
                                          MAKEUNIQUETAG(psKernelSyncInfo->psSyncDataMemInfoKM));
 
-               
+               /* pdump the sync pol: writes */
                PDumpComment("Poll for write ops complete to reach value (pdump: %u, actual snapshot: %u)",
                                         psKernelSyncInfo->psSyncData->ui32LastOpDumpVal,
                                         ui32WriteOpsPendingSnapShot);
@@ -3762,11 +4300,12 @@ static PVRSRV_ERROR DoQuerySyncOpsSatisfied(PVRSRV_KERNEL_SYNC_INFO *psKernelSyn
                                          offsetof(PVRSRV_SYNC_DATA, ui32WriteOpsComplete),
                                          psKernelSyncInfo->psSyncData->ui32LastOpDumpVal,
                                          0xFFFFFFFF,
-                                         PDUMP_POLL_OPERATOR_EQUAL, 
+                                         PDUMP_POLL_OPERATOR_EQUAL, /*  * see "NB" below */
                                          0,
                                          MAKEUNIQUETAG(psKernelSyncInfo->psSyncDataMemInfoKM));
-               
-
+               /* NB: FIXME -- really need to POL on an expression to
+                  accurately reflect the condition we need to check.  How to
+                  do this in PDUMP? */
 #endif
                return PVRSRV_OK;
        }
@@ -3788,20 +4327,21 @@ static PVRSRV_ERROR DoModifyCompleteSyncOps(MODIFY_SYNC_OP_INFO *psModSyncOpInfo
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* If user has used the API correctly, we will always have reached the pending snapshot.
+          We should catch this error on the client side of the bridge and report it in an obvious way */
        if((psModSyncOpInfo->ui32WriteOpsPendingSnapShot != psKernelSyncInfo->psSyncData->ui32WriteOpsComplete)
           || (psModSyncOpInfo->ui32ReadOpsPendingSnapShot != psKernelSyncInfo->psSyncData->ui32ReadOpsComplete))
        {
                return PVRSRV_ERROR_BAD_SYNC_STATE;
        }
 
-       
+       /* update the WOpComplete */
        if(psModSyncOpInfo->ui32ModifyFlags & PVRSRV_MODIFYSYNCOPS_FLAGS_WO_INC)
        {
                psKernelSyncInfo->psSyncData->ui32WriteOpsComplete++;
        }
 
-       
+       /* update the ROpComplete */
        if(psModSyncOpInfo->ui32ModifyFlags & PVRSRV_MODIFYSYNCOPS_FLAGS_RO_INC)
        {
                psKernelSyncInfo->psSyncData->ui32ReadOpsComplete++;
@@ -3830,12 +4370,12 @@ static PVRSRV_ERROR ModifyCompleteSyncOpsCallBack(IMG_PVOID             pvParam,
 
        if (psModSyncOpInfo->psKernelSyncInfo)
        {
-               
                LOOP_UNTIL_TIMEOUT(MAX_HW_TIME_US)
                {
                        if (DoQuerySyncOpsSatisfied(psModSyncOpInfo->psKernelSyncInfo,
                                                                                psModSyncOpInfo->ui32ReadOpsPendingSnapShot,
-                                        psModSyncOpInfo->ui32WriteOpsPendingSnapShot) == PVRSRV_OK)
+                                                                               psModSyncOpInfo->ui32WriteOpsPendingSnapShot,
+                                                                               psModSyncOpInfo->ui32ReadOps2PendingSnapShot) == PVRSRV_OK)
                        {
                                goto OpFlushedComplete;
                        }
@@ -3847,21 +4387,22 @@ static PVRSRV_ERROR ModifyCompleteSyncOpsCallBack(IMG_PVOID             pvParam,
                PVR_DPF((PVR_DBG_ERROR, "  Write ops pending snapshot = %d, write ops complete = %d",
                                 psModSyncOpInfo->ui32WriteOpsPendingSnapShot,
                                 psModSyncOpInfo->psKernelSyncInfo->psSyncData->ui32WriteOpsComplete));
-        PVR_DPF((PVR_DBG_ERROR, "  Read ops pending snapshot = %d, write ops complete = %d",
+               PVR_DPF((PVR_DBG_ERROR, "  Read ops pending snapshot = %d, read ops complete = %d",
                                 psModSyncOpInfo->ui32ReadOpsPendingSnapShot,
                                 psModSyncOpInfo->psKernelSyncInfo->psSyncData->ui32ReadOpsComplete));
-
+               PVR_DPF((PVR_DBG_ERROR, "  Read ops pending snapshot = %d, read ops2 complete = %d",
+                                psModSyncOpInfo->ui32ReadOps2PendingSnapShot,
+                                psModSyncOpInfo->psKernelSyncInfo->psSyncData->ui32ReadOps2Complete));
                return PVRSRV_ERROR_TIMEOUT;
 
 OpFlushedComplete:
-
                DoModifyCompleteSyncOps(psModSyncOpInfo);
+               PVRSRVKernelSyncInfoDecRef(psModSyncOpInfo->psKernelSyncInfo, IMG_NULL);
        }
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,      sizeof(MODIFY_SYNC_OP_INFO), (IMG_VOID *)psModSyncOpInfo, 0);
-       
 
-       
+       /* re-kick all services managed devices */
        PVRSRVScheduleDeviceCallbacks();
 
        return PVRSRV_OK;
@@ -3888,7 +4429,7 @@ PVRSRVCreateSyncInfoModObjBW(IMG_UINT32
                          (IMG_VOID **)&psModSyncOpInfo, 0,
                          "ModSyncOpInfo (MODIFY_SYNC_OP_INFO)"));
 
-       psModSyncOpInfo->psKernelSyncInfo = IMG_NULL; 
+       psModSyncOpInfo->psKernelSyncInfo = IMG_NULL; /* mark it as empty */
 
        psCreateSyncInfoModObjOUT->eError = PVRSRVAllocHandle(psPerProc->psHandleBase,
                                                                                                                                  &psCreateSyncInfoModObjOUT->hKernelSyncInfoModObj,
@@ -3935,11 +4476,13 @@ PVRSRVDestroySyncInfoModObjBW(IMG_UINT32
 
        if(psModSyncOpInfo->psKernelSyncInfo != IMG_NULL)
        {
-               
+               /* Not empty */
                psDestroySyncInfoModObjOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
                return 0;
        }
 
+       PVRSRVKernelSyncInfoDecRef(psModSyncOpInfo->psKernelSyncInfo, IMG_NULL);
+
        psDestroySyncInfoModObjOUT->eError = PVRSRVReleaseHandle(psPerProc->psHandleBase,
                                                                                                                                         psDestroySyncInfoModObjIN->hKernelSyncInfoModObj,
                                                                                                                                         PVRSRV_HANDLE_TYPE_SYNC_INFO_MOD_OBJ);
@@ -3994,22 +4537,33 @@ PVRSRVModifyPendingSyncOpsBW(IMG_UINT32                                                                 ui32BridgeID,
 
        if(psModSyncOpInfo->psKernelSyncInfo)
        {
-               
+               /* SyncInfoModification is not empty */
                psModifySyncOpsOUT->eError = PVRSRV_ERROR_RETRY;
                PVR_DPF((PVR_DBG_VERBOSE, "PVRSRVModifyPendingSyncOpsBW: SyncInfo Modification object is not empty"));
                return 0;
        }
 
-       
+       /* Should never happen, but check to be sure */
+       if (psKernelSyncInfo == IMG_NULL)
+       {
+               psModifySyncOpsOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
+               PVR_DPF((PVR_DBG_VERBOSE, "PVRSRVModifyPendingSyncOpsBW: SyncInfo bad handle"));
+               return 0;
+       }
+
+       PVRSRVKernelSyncInfoIncRef(psKernelSyncInfo, IMG_NULL);
+       /* setup info to store in resman */
        psModSyncOpInfo->psKernelSyncInfo = psKernelSyncInfo;
        psModSyncOpInfo->ui32ModifyFlags = psModifySyncOpsIN->ui32ModifyFlags;
        psModSyncOpInfo->ui32ReadOpsPendingSnapShot = psKernelSyncInfo->psSyncData->ui32ReadOpsPending;
        psModSyncOpInfo->ui32WriteOpsPendingSnapShot = psKernelSyncInfo->psSyncData->ui32WriteOpsPending;
+       psModSyncOpInfo->ui32ReadOps2PendingSnapShot = psKernelSyncInfo->psSyncData->ui32ReadOps2Pending;
 
-       
+       /* We return PRE-INCREMENTED versions of all sync Op Values */
 
        psModifySyncOpsOUT->ui32ReadOpsPending = psKernelSyncInfo->psSyncData->ui32ReadOpsPending;
        psModifySyncOpsOUT->ui32WriteOpsPending = psKernelSyncInfo->psSyncData->ui32WriteOpsPending;
+       psModifySyncOpsOUT->ui32ReadOps2Pending = psKernelSyncInfo->psSyncData->ui32ReadOps2Pending;
 
        if(psModifySyncOpsIN->ui32ModifyFlags & PVRSRV_MODIFYSYNCOPS_FLAGS_WO_INC)
        {
@@ -4021,7 +4575,7 @@ PVRSRVModifyPendingSyncOpsBW(IMG_UINT32                                                                   ui32BridgeID,
                psKernelSyncInfo->psSyncData->ui32ReadOpsPending++;
        }
 
-       
+       /* pull the resman item to the front of the list */
        psModifySyncOpsOUT->eError = ResManDissociateRes(psModSyncOpInfo->hResItem,
                                                                                                         psPerProc->hResManContext);
 
@@ -4057,7 +4611,7 @@ PVRSRVModifyCompleteSyncOpsBW(IMG_UINT32                                                  ui32BridgeID,
 
        if(psModSyncOpInfo->psKernelSyncInfo == IMG_NULL)
        {
-               
+               /* Empty */
                psModifySyncOpsOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
                return 0;
        }
@@ -4070,9 +4624,10 @@ PVRSRVModifyCompleteSyncOpsBW(IMG_UINT32                                                 ui32BridgeID,
                return 0;
        }
 
+       PVRSRVKernelSyncInfoDecRef(psModSyncOpInfo->psKernelSyncInfo, IMG_NULL);
        psModSyncOpInfo->psKernelSyncInfo = IMG_NULL;
 
-       
+       /* re-kick all services managed devices */
        PVRSRVScheduleDeviceCallbacks();
 
        return 0;
@@ -4099,10 +4654,11 @@ PVRSRVSyncOpsTakeTokenBW(IMG_UINT32                                                                     ui32BridgeID,
                return 0;
        }
 
-       
+       /* We return PRE-INCREMENTED versions of all sync Op Values */
 
        psSyncOpsTakeTokenOUT->ui32ReadOpsPending = psKernelSyncInfo->psSyncData->ui32ReadOpsPending;
        psSyncOpsTakeTokenOUT->ui32WriteOpsPending = psKernelSyncInfo->psSyncData->ui32WriteOpsPending;
+       psSyncOpsTakeTokenOUT->ui32ReadOps2Pending = psKernelSyncInfo->psSyncData->ui32ReadOps2Pending;
 
        return 0;
 }
@@ -4117,6 +4673,7 @@ PVRSRVSyncOpsFlushToTokenBW(IMG_UINT32                                         u
        PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo;
        IMG_UINT32 ui32ReadOpsPendingSnapshot;
        IMG_UINT32 ui32WriteOpsPendingSnapshot;
+       IMG_UINT32 ui32ReadOps2PendingSnapshot;
 
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_SYNC_OPS_FLUSH_TO_TOKEN);
 
@@ -4132,10 +4689,12 @@ PVRSRVSyncOpsFlushToTokenBW(IMG_UINT32                                         u
 
        ui32ReadOpsPendingSnapshot = psSyncOpsFlushToTokenIN->ui32ReadOpsPendingSnapshot;
        ui32WriteOpsPendingSnapshot = psSyncOpsFlushToTokenIN->ui32WriteOpsPendingSnapshot;
+       ui32ReadOps2PendingSnapshot = psSyncOpsFlushToTokenIN->ui32ReadOps2PendingSnapshot;
 
        psSyncOpsFlushToTokenOUT->eError = DoQuerySyncOpsSatisfied(psKernelSyncInfo,
                                                                                                                           ui32ReadOpsPendingSnapshot,
-                                                               ui32WriteOpsPendingSnapshot);
+                                                                                                                          ui32WriteOpsPendingSnapshot,
+                                                                                                                          ui32ReadOps2PendingSnapshot);
 
        if (psSyncOpsFlushToTokenOUT->eError != PVRSRV_OK && psSyncOpsFlushToTokenOUT->eError != PVRSRV_ERROR_RETRY)
        {
@@ -4169,14 +4728,15 @@ PVRSRVSyncOpsFlushToModObjBW(IMG_UINT32
 
        if(psModSyncOpInfo->psKernelSyncInfo == IMG_NULL)
        {
-               
+               /* Empty */
                psSyncOpsFlushToModObjOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
                return 0;
        }
 
        psSyncOpsFlushToModObjOUT->eError = DoQuerySyncOpsSatisfied(psModSyncOpInfo->psKernelSyncInfo,
                                                                                                                                psModSyncOpInfo->ui32ReadOpsPendingSnapShot,
-                                                                psModSyncOpInfo->ui32WriteOpsPendingSnapShot);
+                                                                                                                               psModSyncOpInfo->ui32WriteOpsPendingSnapShot,
+                                                                                                                               psModSyncOpInfo->ui32ReadOps2PendingSnapShot);
 
        if (psSyncOpsFlushToModObjOUT->eError != PVRSRV_OK && psSyncOpsFlushToModObjOUT->eError != PVRSRV_ERROR_RETRY)
        {
@@ -4210,14 +4770,16 @@ PVRSRVSyncOpsFlushToDeltaBW(IMG_UINT32                                         u
                return 0;
        }
 
-       
+       /* FIXME:  there's logic here in the bridge-wrapper - this needs to be moved to
+          a better place */
+
        ui32DeltaRead = psSyncInfo->psSyncData->ui32ReadOpsPending - psSyncInfo->psSyncData->ui32ReadOpsComplete;
        ui32DeltaWrite = psSyncInfo->psSyncData->ui32WriteOpsPending - psSyncInfo->psSyncData->ui32WriteOpsComplete;
 
        if (ui32DeltaRead <= psSyncOpsFlushToDeltaIN->ui32Delta && ui32DeltaWrite <= psSyncOpsFlushToDeltaIN->ui32Delta)
        {
 #if defined(PDUMP) && !defined(SUPPORT_VGX)
-               
+               /* pdump the sync pol: reads */
                PDumpComment("Poll for read ops complete to delta (%u)",
                                         psSyncOpsFlushToDeltaIN->ui32Delta);
                psSyncOpsFlushToDeltaOUT->eError =
@@ -4229,7 +4791,7 @@ PVRSRVSyncOpsFlushToDeltaBW(IMG_UINT32                                         u
                                                  0,
                                                  MAKEUNIQUETAG(psSyncInfo->psSyncDataMemInfoKM));
 
-               
+               /* pdump the sync pol: writes */
                PDumpComment("Poll for write ops complete to delta (%u)",
                                         psSyncOpsFlushToDeltaIN->ui32Delta);
                psSyncOpsFlushToDeltaOUT->eError =
@@ -4259,18 +4821,13 @@ FreeSyncInfoCallback(IMG_PVOID  pvParam,
                      IMG_BOOL  bDummy)
 {
        PVRSRV_KERNEL_SYNC_INFO *psSyncInfo;
-       PVRSRV_ERROR eError;
 
        PVR_UNREFERENCED_PARAMETER(ui32Param);
     PVR_UNREFERENCED_PARAMETER(bDummy);
 
        psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)pvParam;
 
-       eError = PVRSRVFreeSyncInfoKM(psSyncInfo);
-       if (eError != PVRSRV_OK)
-       {
-               return eError;
-       }
+       PVRSRVKernelSyncInfoDecRef(psSyncInfo, IMG_NULL);
 
        return PVRSRV_OK;
 }
@@ -4326,18 +4883,18 @@ PVRSRVAllocSyncInfoBW(IMG_UINT32                                         ui32Bri
                                                                                           RESMAN_TYPE_SYNC_INFO,
                                                                                           psSyncInfo,
                                                                                           0,
-                                                                                          FreeSyncInfoCallback);
+                                                                                          &FreeSyncInfoCallback);
 
-       
+       /* Success */
        goto allocsyncinfo_commit;
 
-       
+       /* Error handling */
  allocsyncinfo_errorexit_freesyncinfo:
-       PVRSRVFreeSyncInfoKM(psSyncInfo);
+       PVRSRVKernelSyncInfoDecRef(psSyncInfo, IMG_NULL);
 
  allocsyncinfo_errorexit:
 
-       
+       /* Common exit */
  allocsyncinfo_commit:
        psAllocSyncInfoOUT->eError = eError;
        COMMIT_HANDLE_BATCH_OR_ERROR(eError, psPerProc);
@@ -4427,31 +4984,35 @@ CommonBridgeInit(IMG_VOID)
     SetDispatchTableEntry(PVRSRV_BRIDGE_CHG_DEV_MEM_ATTRIBS, PVRSRVChangeDeviceMemoryAttributesBW);
     SetDispatchTableEntry(PVRSRV_BRIDGE_MAP_DEV_MEMORY_2, PVRSRVMapDeviceMemoryBW);
     SetDispatchTableEntry(PVRSRV_BRIDGE_EXPORT_DEVICEMEM_2, PVRSRVExportDeviceMemBW);
+#if defined(SUPPORT_ION)
+       SetDispatchTableEntry(PVRSRV_BRIDGE_MAP_ION_HANDLE, PVRSRVMapIonHandleBW);
+       SetDispatchTableEntry(PVRSRV_BRIDGE_UNMAP_ION_HANDLE, PVRSRVUnmapIonHandleBW);
+#endif
 
-       
+       /* SIM */
        SetDispatchTableEntry(PVRSRV_BRIDGE_PROCESS_SIMISR_EVENT, DummyBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_REGISTER_SIM_PROCESS, DummyBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_UNREGISTER_SIM_PROCESS, DummyBW);
 
-       
+       /* User Mapping */
        SetDispatchTableEntry(PVRSRV_BRIDGE_MAPPHYSTOUSERSPACE, DummyBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_UNMAPPHYSTOUSERSPACE, DummyBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_GETPHYSTOUSERSPACEMAP, DummyBW);
 
        SetDispatchTableEntry(PVRSRV_BRIDGE_GET_FB_STATS, DummyBW);
 
-       
+       /* API to retrieve misc. info. from services */
        SetDispatchTableEntry(PVRSRV_BRIDGE_GET_MISC_INFO, PVRSRVGetMiscInfoBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_RELEASE_MISC_INFO, DummyBW);
 
-       
+       /* Overlay ioctls */
 #if defined (SUPPORT_OVERLAY_ROTATE_BLIT)
        SetDispatchTableEntry(PVRSRV_BRIDGE_INIT_3D_OVL_BLT_RES, DummyBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_DEINIT_3D_OVL_BLT_RES, DummyBW);
 #endif
 
 
-       
+       /* PDUMP */
 #if defined(PDUMP)
        SetDispatchTableEntry(PVRSRV_BRIDGE_PDUMP_INIT, DummyBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_PDUMP_MEMPOL, PDumpMemPolBW);
@@ -4471,20 +5032,24 @@ CommonBridgeInit(IMG_VOID)
        SetDispatchTableEntry(PVRSRV_BRIDGE_PDUMP_CYCLE_COUNT_REG_READ, PDumpCycleCountRegReadBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_PDUMP_STARTINITPHASE, PDumpStartInitPhaseBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_PDUMP_STOPINITPHASE, PDumpStopInitPhaseBW);
-#endif 
+#endif /* defined(PDUMP) */
 
-       
+       /* DisplayClass APIs */
        SetDispatchTableEntry(PVRSRV_BRIDGE_GET_OEMJTABLE, DummyBW);
 
-       
+       /* device class enum */
        SetDispatchTableEntry(PVRSRV_BRIDGE_ENUM_CLASS, PVRSRVEnumerateDCBW);
 
-       
+       /* display class API */
        SetDispatchTableEntry(PVRSRV_BRIDGE_OPEN_DISPCLASS_DEVICE, PVRSRVOpenDCDeviceBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_CLOSE_DISPCLASS_DEVICE, PVRSRVCloseDCDeviceBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_ENUM_DISPCLASS_FORMATS, PVRSRVEnumDCFormatsBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_ENUM_DISPCLASS_DIMS, PVRSRVEnumDCDimsBW);
+#if defined(SUPPORT_PVRSRV_GET_DC_SYSTEM_BUFFER)
        SetDispatchTableEntry(PVRSRV_BRIDGE_GET_DISPCLASS_SYSBUFFER, PVRSRVGetDCSystemBufferBW);
+#else
+       SetDispatchTableEntry(PVRSRV_BRIDGE_GET_DISPCLASS_SYSBUFFER, DummyBW);
+#endif
        SetDispatchTableEntry(PVRSRV_BRIDGE_GET_DISPCLASS_INFO, PVRSRVGetDCInfoBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_CREATE_DISPCLASS_SWAPCHAIN, PVRSRVCreateDCSwapChainBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_DESTROY_DISPCLASS_SWAPCHAIN, PVRSRVDestroyDCSwapChainBW);
@@ -4494,28 +5059,29 @@ CommonBridgeInit(IMG_VOID)
        SetDispatchTableEntry(PVRSRV_BRIDGE_SET_DISPCLASS_SRCCOLOURKEY, PVRSRVSetDCSrcColourKeyBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_GET_DISPCLASS_BUFFERS, PVRSRVGetDCBuffersBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_SWAP_DISPCLASS_TO_BUFFER, PVRSRVSwapToDCBufferBW);
+       SetDispatchTableEntry(PVRSRV_BRIDGE_SWAP_DISPCLASS_TO_BUFFER2, PVRSRVSwapToDCBuffer2BW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_SWAP_DISPCLASS_TO_SYSTEM, PVRSRVSwapToDCSystemBW);
 
-       
+       /* buffer class API */
        SetDispatchTableEntry(PVRSRV_BRIDGE_OPEN_BUFFERCLASS_DEVICE, PVRSRVOpenBCDeviceBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_CLOSE_BUFFERCLASS_DEVICE, PVRSRVCloseBCDeviceBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_GET_BUFFERCLASS_INFO, PVRSRVGetBCInfoBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_GET_BUFFERCLASS_BUFFER, PVRSRVGetBCBufferBW);
 
-       
+       /* Wrap/Unwrap external memory */
        SetDispatchTableEntry(PVRSRV_BRIDGE_WRAP_EXT_MEMORY, PVRSRVWrapExtMemoryBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_UNWRAP_EXT_MEMORY, PVRSRVUnwrapExtMemoryBW);
 
-       
+       /* Shared memory */
        SetDispatchTableEntry(PVRSRV_BRIDGE_ALLOC_SHARED_SYS_MEM, PVRSRVAllocSharedSysMemoryBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_FREE_SHARED_SYS_MEM, PVRSRVFreeSharedSysMemoryBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_MAP_MEMINFO_MEM, PVRSRVMapMemInfoMemBW);
 
-       
+       /* Intialisation Service support */
        SetDispatchTableEntry(PVRSRV_BRIDGE_INITSRV_CONNECT,    &PVRSRVInitSrvConnectBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_INITSRV_DISCONNECT, &PVRSRVInitSrvDisconnectBW);
 
-       
+       /* Event Object */
        SetDispatchTableEntry(PVRSRV_BRIDGE_EVENT_OBJECT_WAIT,  &PVRSRVEventObjectWaitBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_EVENT_OBJECT_OPEN,  &PVRSRVEventObjectOpenBW);
        SetDispatchTableEntry(PVRSRV_BRIDGE_EVENT_OBJECT_CLOSE, &PVRSRVEventObjectCloseBW);
@@ -4541,9 +5107,11 @@ CommonBridgeInit(IMG_VOID)
        SetMSVDXDispatchTableEntry();
 #endif
 
-
-       
-       
+       /* A safety net to help ensure there won't be any un-initialised dispatch
+        * table entries... */
+       /* Note: This is specifically done _after_ setting all the dispatch entries
+        * so that SetDispatchTableEntry can detect mistakes where entries
+        * overlap */
        for(i=0;i<BRIDGE_DISPATCH_TABLE_ENTRY_COUNT;i++)
        {
                if(!g_BridgeDispatchTable[i].pfFunction)
@@ -4565,7 +5133,6 @@ CommonBridgeInit(IMG_VOID)
 IMG_INT BridgedDispatchKM(PVRSRV_PER_PROCESS_DATA * psPerProc,
                                          PVRSRV_BRIDGE_PACKAGE   * psBridgePackageKM)
 {
-
        IMG_VOID   * psBridgeIn;
        IMG_VOID   * psBridgeOut;
        BridgeWrapperFunction pfBridgeHandler;
@@ -4604,7 +5171,7 @@ IMG_INT BridgedDispatchKM(PVRSRV_PER_PROCESS_DATA * psPerProc,
                        }
                        else
                        {
-                               
+                               /* Only certain operations are allowed */
                                switch(ui32BridgeID)
                                {
                                        case PVRSRV_GET_BRIDGE_ID(PVRSRV_BRIDGE_CONNECT_SERVICES):
@@ -4621,20 +5188,18 @@ IMG_INT BridgedDispatchKM(PVRSRV_PER_PROCESS_DATA * psPerProc,
                }
        }
 
-
-
 #if defined(__linux__)
        {
-               
+               /* This should be moved into the linux specific code */
                SYS_DATA *psSysData;
 
                SysAcquireData(&psSysData);
 
-               
+               /* We have already set up some static buffers to store our ioctl data... */
                psBridgeIn = ((ENV_DATA *)psSysData->pvEnvSpecificData)->pvBridgeData;
                psBridgeOut = (IMG_PVOID)((IMG_PBYTE)psBridgeIn + PVRSRV_MAX_BRIDGE_IN_SIZE);
 
-               
+               /* check we are not using a bigger bridge than allocated */
                if((psBridgePackageKM->ui32InBufferSize > PVRSRV_MAX_BRIDGE_IN_SIZE) || 
                        (psBridgePackageKM->ui32OutBufferSize > PVRSRV_MAX_BRIDGE_OUT_SIZE))
                {
@@ -4684,9 +5249,8 @@ IMG_INT BridgedDispatchKM(PVRSRV_PER_PROCESS_DATA * psPerProc,
                goto return_fault;
        }
 
-
 #if defined(__linux__)
-       
+       /* This should be moved into the linux specific code */
        if(CopyToUserWrapper(psPerProc,
                                                 ui32BridgeID,
                                                 psBridgePackageKM->pvParamOut,
@@ -4705,3 +5269,6 @@ return_fault:
        return err;
 }
 
+/******************************************************************************
+ End of file (bridged_pvr_bridge.c)
+******************************************************************************/
index 6b0dd88..b0145f7 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PVR Bridge Functionality
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Header for the PVR Bridge code
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __BRIDGED_PVR_BRIDGE_H__
 #define __BRIDGED_PVR_BRIDGE_H__
@@ -138,11 +154,11 @@ ReleaseHandleBatch(PVRSRV_PER_PROCESS_DATA *psPerProc)
                PVRSRVReleaseHandleBatch(psPerProc->psHandleBase);
        }
 }
-#else  
+#else  /* defined(PVR_SECURE_HANDLES) */
 #define NEW_HANDLE_BATCH_OR_ERROR(error, psPerProc, ui32BatchSize)
 #define COMMIT_HANDLE_BATCH_OR_ERROR(error, psPerProc)
 #define ReleaseHandleBatch(psPerProc)
-#endif 
+#endif /* defined(PVR_SECURE_HANDLES) */
 
 IMG_INT
 DummyBW(IMG_UINT32 ui32BridgeID,
@@ -157,13 +173,16 @@ typedef IMG_INT (*BridgeWrapperFunction)(IMG_UINT32 ui32BridgeID,
 
 typedef struct _PVRSRV_BRIDGE_DISPATCH_TABLE_ENTRY
 {
-       BridgeWrapperFunction pfFunction; 
+       BridgeWrapperFunction pfFunction; /*!< The wrapper function that validates the ioctl
+                                                                               arguments before calling into srvkm proper */
 #if defined(DEBUG_BRIDGE_KM)
-       const IMG_CHAR *pszIOCName; 
-       const IMG_CHAR *pszFunctionName; 
-       IMG_UINT32 ui32CallCount; 
-       IMG_UINT32 ui32CopyFromUserTotalBytes; 
-       IMG_UINT32 ui32CopyToUserTotalBytes; 
+       const IMG_CHAR *pszIOCName; /*!< Name of the ioctl: e.g. "PVRSRV_BRIDGE_CONNECT_SERVICES" */
+       const IMG_CHAR *pszFunctionName; /*!< Name of the wrapper function: e.g. "PVRSRVConnectBW" */
+       IMG_UINT32 ui32CallCount; /*!< The total number of times the ioctl has been called */
+       IMG_UINT32 ui32CopyFromUserTotalBytes; /*!< The total number of bytes copied from
+                                                                                        userspace within this ioctl */
+       IMG_UINT32 ui32CopyToUserTotalBytes; /*!< The total number of bytes copied from
+                                                                                  userspace within this ioctl */
 #endif
 }PVRSRV_BRIDGE_DISPATCH_TABLE_ENTRY;
 
@@ -194,7 +213,7 @@ _SetDispatchTableEntry(IMG_UINT32 ui32Index,
                                           const IMG_CHAR *pszFunctionName);
 
 
+/* PRQA S 0884,3410 2*/ /* macro relies on the lack of brackets */
 #define SetDispatchTableEntry(ui32Index, pfFunction) \
        _SetDispatchTableEntry(PVRSRV_GET_BRIDGE_ID(ui32Index), #ui32Index, (BridgeWrapperFunction)pfFunction, #pfFunction)
 
@@ -215,6 +234,9 @@ typedef struct _PVRSRV_BRIDGE_GLOBAL_STATS
        IMG_UINT32 ui32TotalCopyToUserBytes;
 }PVRSRV_BRIDGE_GLOBAL_STATS;
 
+/* OS specific code way want to report the stats held here and within the
+ * BRIDGE_DISPATCH_TABLE_ENTRYs (E.g. on Linux we report these via a
+ * proc entry /proc/pvr/bridge_stats. Ref printLinuxBridgeStats()) */
 extern PVRSRV_BRIDGE_GLOBAL_STATS g_BridgeGlobalStats;
 #endif
 
@@ -228,5 +250,8 @@ IMG_INT BridgedDispatchKM(PVRSRV_PER_PROCESS_DATA * psPerProc,
 }
 #endif
 
-#endif 
+#endif /* __BRIDGED_PVR_BRIDGE_H__ */
 
+/******************************************************************************
+ End of file (bridged_pvr_bridge.h)
+******************************************************************************/
index dad0800..25baf29 100644 (file)
@@ -1,34 +1,56 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PVR Bridge Support Functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    User/kernel mode bridge support.  The functions in here
+                may be used beyond the bridge code proper (e.g. Linux
+                mmap interface).
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "img_defs.h"
 #include "servicesint.h"
 #include "bridged_support.h"
 
 
+/*
+ * Derive the internal OS specific memory handle from a secure
+ * handle.
+ */
 PVRSRV_ERROR
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRVLookupOSMemHandle(PVRSRV_HANDLE_BASE *psHandleBase, IMG_HANDLE *phOSMemHandle, IMG_SID hMHandle)
@@ -40,7 +62,10 @@ PVRSRVLookupOSMemHandle(PVRSRV_HANDLE_BASE *psHandleBase, IMG_HANDLE *phOSMemHan
        PVRSRV_HANDLE_TYPE eHandleType;
        PVRSRV_ERROR eError;
 
-       
+       /*
+        * We don't know the type of the handle at this point, so we use
+        * PVRSRVLookupHandleAnyType to look it up.
+        */
        eError = PVRSRVLookupHandleAnyType(psHandleBase, &hMHandleInt,
                                                          &eHandleType,
                                                          hMHandle);
@@ -87,3 +112,6 @@ PVRSRVLookupOSMemHandle(PVRSRV_HANDLE_BASE *psHandleBase, IMG_HANDLE *phOSMemHan
 
        return PVRSRV_OK;
 }
+/******************************************************************************
+ End of file (bridged_support.c)
+******************************************************************************/
index d027290..04d5168 100644 (file)
@@ -1,28 +1,46 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PVR Bridge Support
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    User/kernel mode bridge support.  The functions in here
+                may be used beyond the bridge code proper (e.g. Linux
+                mmap interface).
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __BRIDGED_SUPPORT_H__
 #define __BRIDGED_SUPPORT_H__
 extern "C" {
 #endif
 
+/*
+ * Derive the internal OS specific memory handle from a secure
+ * handle.
+ */
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVLookupOSMemHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phOSMemHandle, IMG_SID hMHandle);
 #else
@@ -43,5 +65,8 @@ PVRSRV_ERROR PVRSRVLookupOSMemHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phO
 }
 #endif
 
-#endif 
+#endif /* __BRIDGED_SUPPORT_H__ */
 
+/******************************************************************************
+ End of file (bridged_support.h)
+******************************************************************************/
index 9989bc5..d2ea7e1 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX Common Bridge Module (kernel side)
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Receives calls from the user portion of services and
+                despatches them to functions in the kernel portion.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 
 
@@ -103,7 +120,9 @@ SGXReleaseClientInfoBW(IMG_UINT32 ui32BridgeID,
 
        PVR_ASSERT(psDevInfo->ui32ClientRefCount > 0);
 
-       
+       /* 
+        * psDevInfo->ui32ClientRefCount can be zero if an error occurred before SGXGetClientInfo is called
+        */
        if (psDevInfo->ui32ClientRefCount > 0)
        {
                psDevInfo->ui32ClientRefCount--;
@@ -146,7 +165,10 @@ SGXGetInternalDevInfoBW(IMG_UINT32 ui32BridgeID,
                                                                &psSGXGetInternalDevInfoOUT->sSGXInternalDevInfo);
 #endif
 
-       
+       /*
+        * Handle is not allocated in batch mode, as there is no resource
+        * allocation to undo if the handle allocation fails.
+        */
        psSGXGetInternalDevInfoOUT->eError =
                PVRSRVAllocHandle(psPerProc->psHandleBase,
                                                  &psSGXGetInternalDevInfoOUT->sSGXInternalDevInfo.hHostCtlKernelMemInfoHandle,
@@ -257,7 +279,7 @@ SGXDoKickBW(IMG_UINT32 ui32BridgeID,
        }
 
 #if defined(FIX_HW_BRN_31620)
-       
+       /* We need to lookup the mem context and pass it through */
        psRetOUT->eError =
                PVRSRVLookupHandle(psPerProc->psHandleBase,
                                                   &psDoKickIN->sCCBKick.hDevMemContext,
@@ -294,7 +316,7 @@ SGXDoKickBW(IMG_UINT32 ui32BridgeID,
 
 
 #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS)
-       
+       /* SRC and DST sync details */
        if (psDoKickIN->sCCBKick.ui32NumTASrcSyncs > SGX_MAX_TA_SRC_SYNCS)
        {
                psRetOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
@@ -375,9 +397,9 @@ SGXDoKickBW(IMG_UINT32 ui32BridgeID,
                        return 0;
                }
        }
-#else
-       
-       if (psDoKickIN->sCCBKick.ui32NumSrcSyncs > SGX_MAX_SRC_SYNCS)
+#else/* #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS) */
+       /* texture dependency details */
+       if (psDoKickIN->sCCBKick.ui32NumSrcSyncs > SGX_MAX_SRC_SYNCS_TA)
        {
                psRetOUT->eError = PVRSRV_ERROR_INVALID_PARAMS;
                return 0;
@@ -403,7 +425,7 @@ SGXDoKickBW(IMG_UINT32 ui32BridgeID,
                        return 0;
                }
        }
-#endif
+#endif/* #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS) */
 
        if (psDoKickIN->sCCBKick.ui32NumTAStatusVals > SGX_MAX_TA_STATUS_VALS)
        {
@@ -517,7 +539,7 @@ SGXDoKickBW(IMG_UINT32 ui32BridgeID,
                        goto PVRSRV_BRIDGE_SGX_DOKICK_RETURN_RESULT;
                }
 
-               
+               /* Set sCCBKick.pahDstSyncHandles to point to the local memory */
                psDoKickIN->sCCBKick.pahDstSyncHandles = phKernelSyncInfoHandles;
 #endif
 
@@ -566,7 +588,7 @@ SGXDoKickBW(IMG_UINT32 ui32BridgeID,
        sCCBKickKM.ui32CCBOffset         = psDoKickIN->sCCBKick.ui32CCBOffset;
        sCCBKickKM.bTADependency         = psDoKickIN->sCCBKick.bTADependency;
 
-#if (defined(NO_HARDWARE) || defined(PDUMP))
+#if defined(NO_HARDWARE) || defined(PDUMP)
        sCCBKickKM.bTerminateOrAbort = psDoKickIN->sCCBKick.bTerminateOrAbort;
 #endif
 #if defined(PDUMP)
@@ -576,7 +598,7 @@ SGXDoKickBW(IMG_UINT32 ui32BridgeID,
 #if defined(NO_HARDWARE)
        sCCBKickKM.ui32WriteOpsPendingVal = psDoKickIN->sCCBKick.ui32WriteOpsPendingVal;
 #endif
-#endif 
+#endif /* #if defined (SUPPORT_SID_INTERFACE) */
        psRetOUT->eError =
                SGXDoKickKM(hDevCookieInt,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -587,13 +609,14 @@ SGXDoKickBW(IMG_UINT32 ui32BridgeID,
 
 PVRSRV_BRIDGE_SGX_DOKICK_RETURN_RESULT:
 
+//#if (!defined(_UITRON_) && !defined(UNDER_VISTA)) || defined (SUPPORT_SID_INTERFACE)
        if(phKernelSyncInfoHandles)
        {
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
                                  ui32NumDstSyncs * sizeof(IMG_HANDLE),
                                  (IMG_VOID *)phKernelSyncInfoHandles,
                                  0);
-               
+               /*not nulling pointer, out of scope*/
        }
        return ret;
 }
@@ -646,7 +669,7 @@ SGXSubmitTransferBW(IMG_UINT32 ui32BridgeID,
        psKick = &psSubmitTransferIN->sKick;
 
 #if defined(FIX_HW_BRN_31620)
-       
+       /* We need to lookup the mem context and pass it through */
        psRetOUT->eError =
                PVRSRVLookupHandle(psPerProc->psHandleBase,
                                                   &psKick->hDevMemContext,
@@ -885,7 +908,7 @@ SGXSubmit2DBW(IMG_UINT32 ui32BridgeID,
        psKick = &psSubmit2DIN->sKick;
 
 #if defined(FIX_HW_BRN_31620)
-       
+       /* We need to lookup the mem context and pass it through */
        psRetOUT->eError =
                PVRSRVLookupHandle(psPerProc->psHandleBase,
                                                   &psKick->hDevMemContext,
@@ -1037,7 +1060,7 @@ SGXSubmit2DBW(IMG_UINT32 ui32BridgeID,
                sKickKM.hDstSyncInfo = IMG_NULL;
        }
 
-       
+       /* copy common members across */
        sKickKM.ui32SharedCmdCCBOffset = psKick->ui32SharedCmdCCBOffset;
        sKickKM.ui32NumSrcSync         = psKick->ui32NumSrcSync;
        sKickKM.ui32PDumpFlags         = psKick->ui32PDumpFlags;
@@ -1056,8 +1079,8 @@ SGXSubmit2DBW(IMG_UINT32 ui32BridgeID,
 
        return 0;
 }
-#endif 
-#endif 
+#endif /* #if defined(SGX_FEATURE_2D_HARDWARE) */
+#endif /* #if defined(TRANSFER_QUEUE) */
 
 
 static IMG_INT
@@ -1086,7 +1109,7 @@ SGXGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
        }
 
 #if defined(SUPPORT_SGX_EDM_MEMORY_DEBUG)
-       
+       /* Lookup handle for dev mem context */
        if (psSGXGetMiscInfoIN->psMiscInfo->eRequest == SGX_MISC_INFO_REQUEST_MEMREAD)
        {
                psRetOUT->eError = PVRSRVLookupHandle(psPerProc->psHandleBase,
@@ -1100,7 +1123,7 @@ SGXGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
                }
        }
 #endif
-       
+       /* device node is required for scheduling a CCB command */
        psDeviceNode = hDevCookieInt;
        PVR_ASSERT(psDeviceNode != IMG_NULL);
        if (psDeviceNode == IMG_NULL)
@@ -1110,7 +1133,7 @@ SGXGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
 
        psDevInfo = psDeviceNode->pvDevice;
 
-       
+       /* Copy psMiscInfo to kernel space */
        psRetOUT->eError = CopyFromUserWrapper(psPerProc,
                                                       ui32BridgeID,
                                                       &sMiscInfo,
@@ -1130,7 +1153,7 @@ SGXGetMiscInfoBW(IMG_UINT32 ui32BridgeID,
                }
        }
 
-       
+       /* Copy back misc info to user address space */
        psRetOUT->eError = CopyToUserWrapper(psPerProc,
                                             ui32BridgeID,
                                             psSGXGetMiscInfoIN->psMiscInfo,
@@ -1195,7 +1218,7 @@ SGXReadHWPerfCBBW(IMG_UINT32                                                      ui32BridgeID,
                          ui32AllocatedSize,
                          psAllocated,
                          hAllocatedHandle);
-       
+       /*not nulling pointer, out of scope*/
 
        return 0;
 }
@@ -1224,7 +1247,7 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
 
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_SGX_DEVINITPART2);
 
-       
+       /* Report the kernel-side build options to UM */
        psSGXDevInitPart2OUT->ui32KMBuildOptions = SGX_BUILD_OPTIONS;
 
        if(!psPerProc->bInitProcess)
@@ -1243,7 +1266,7 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
+       /* Check all the meminfo handles */
        eError = PVRSRVLookupHandle(psPerProc->psHandleBase,
                                                   &hDummy,
                                                   psSGXDevInitPart2IN->sInitInfo.hKernelCCBMemInfo,
@@ -1327,6 +1350,7 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
                                                   PVRSRV_HANDLE_TYPE_MEM_INFO);
        if (eError != PVRSRV_OK)
        {
+               PVR_DPF((PVR_DBG_ERROR, "SGXDevInitPart2BW: Failed to look up HWPerf meminfo (possibly due to SUPPORT_SGX_HWPERF option mismatch)"));
                bLookupFailed = IMG_TRUE;
        }
 #endif
@@ -1440,7 +1464,7 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
        }
 #endif
 
-#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31425)
+#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31559)
        eError = PVRSRVLookupHandle(psPerProc->psHandleBase,
                                                   &hDummy,
                                                   psSGXDevInitPart2IN->sInitInfo.hKernelVDMSnapShotBufferMemInfo,
@@ -1511,12 +1535,12 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
 
        if (bLookupFailed)
        {
-               PVR_DPF((PVR_DBG_ERROR, "DevInitSGXPart2BW: A handle lookup failed"));
+               PVR_DPF((PVR_DBG_ERROR, "SGXDevInitPart2BW: A handle lookup failed"));
                psSGXDevInitPart2OUT->eError = PVRSRV_ERROR_INIT2_PHASE_FAILED;
                return 0;
        }
 
-       
+       /* Lookup and release the device memory handles */
        eError = PVRSRVLookupAndReleaseHandle(psPerProc->psHandleBase,
 #if defined (SUPPORT_SID_INTERFACE)
                                                   &asInitInfoKM.hKernelCCBMemInfo,
@@ -1797,7 +1821,7 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
                bReleaseFailed = IMG_TRUE;
        }
 #endif
-#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31425)
+#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31559)
        eError = PVRSRVLookupAndReleaseHandle(psPerProc->psHandleBase,
                                                   &psSGXDevInitPart2IN->sInitInfo.hKernelVDMSnapShotBufferMemInfo,
                                                   psSGXDevInitPart2IN->sInitInfo.hKernelVDMSnapShotBufferMemInfo,
@@ -1874,14 +1898,17 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
 
        if (bReleaseFailed)
        {
-               PVR_DPF((PVR_DBG_ERROR, "DevInitSGXPart2BW: A handle release failed"));
+               PVR_DPF((PVR_DBG_ERROR, "SGXDevInitPart2BW: A handle release failed"));
                psSGXDevInitPart2OUT->eError = PVRSRV_ERROR_INIT2_PHASE_FAILED;
-               
+               /*
+                * Given that we checked the handles before release, a release
+                * failure is unexpected.
+                */
                PVR_DBG_BREAK;
                return 0;
        }
 
-       
+       /* Dissociate device memory from caller */
 #if defined (SUPPORT_SID_INTERFACE)
        eError = PVRSRVDissociateDeviceMemKM(hDevCookieInt, asInitInfoKM.hKernelCCBMemInfo);
 #else
@@ -1944,7 +1971,7 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
        }
 #endif
 
-       
+       /* Dissociate SGX MiscInfo buffer from user space */
 #if defined (SUPPORT_SID_INTERFACE)
        eError = PVRSRVDissociateDeviceMemKM(hDevCookieInt, asInitInfoKM.hKernelSGXMiscMemInfo);
 #else
@@ -2110,7 +2137,7 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
 #endif
 #endif
 
-#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31425)
+#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31559)
        eError = PVRSRVDissociateDeviceMemKM(hDevCookieInt, psSGXDevInitPart2IN->sInitInfo.hKernelVDMSnapShotBufferMemInfo);
        bDissociateFailed |= (IMG_BOOL)(eError != PVRSRV_OK);
        
@@ -2154,7 +2181,7 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
                }
        }
 
-       
+       /* If any dissociations failed, free all the device memory passed in */
        if(bDissociateFailed)
        {
 #if defined (SUPPORT_SID_INTERFACE)
@@ -2194,11 +2221,11 @@ SGXDevInitPart2BW(IMG_UINT32 ui32BridgeID,
 
                }
 
-               PVR_DPF((PVR_DBG_ERROR, "DevInitSGXPart2BW: A dissociate failed"));
+               PVR_DPF((PVR_DBG_ERROR, "SGXDevInitPart2BW: A dissociate failed"));
 
                psSGXDevInitPart2OUT->eError = PVRSRV_ERROR_INIT2_PHASE_FAILED;
 
-               
+               /* A dissociation failure is unexpected */
                PVR_DBG_BREAK;
                return 0;
        }
@@ -2242,6 +2269,7 @@ SGXRegisterHWRenderContextBW(IMG_UINT32 ui32BridgeID,
                                                         PVRSRV_PER_PROCESS_DATA *psPerProc)
 {
        IMG_HANDLE hDevCookieInt;
+//     PVRSRV_SGXDEV_INFO *psDevInfo;
        IMG_HANDLE hHWRenderContextInt;
 
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_SGX_REGISTER_HW_RENDER_CONTEXT);
@@ -2496,7 +2524,7 @@ SGXUnregisterHW2DContextBW(IMG_UINT32 ui32BridgeID,
 
        return 0;
 }
-#endif 
+#endif /* #if defined(SGX_FEATURE_2D_HARDWARE) */
 
 static IMG_INT
 SGXFlushHWRenderTargetBW(IMG_UINT32 ui32BridgeID,
@@ -2505,6 +2533,8 @@ SGXFlushHWRenderTargetBW(IMG_UINT32 ui32BridgeID,
                                                  PVRSRV_PER_PROCESS_DATA *psPerProc)
 {
        IMG_HANDLE hDevCookieInt;
+//     PVRSRV_SGXDEV_INFO *psDevInfo;
+
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_SGX_FLUSH_HW_RENDER_TARGET);
 
        psRetOUT->eError =
@@ -2517,6 +2547,8 @@ SGXFlushHWRenderTargetBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
+//     psDevInfo = (PVRSRV_SGXDEV_INFO *)((PVRSRV_DEVICE_NODE *)hDevCookieInt)->pvDevice;
+
        psRetOUT->eError = SGXFlushHWRenderTargetKM(hDevCookieInt, psSGXFlushHWRenderTargetIN->sHWRTDataSetDevVAddr, IMG_FALSE);
 
        return 0;
@@ -2619,7 +2651,8 @@ SGXFindSharedPBDescBW(IMG_UINT32 ui32BridgeID,
        if(hSharedPBDesc == IMG_NULL)
        {
                psSGXFindSharedPBDescOUT->hSharedPBDescKernelMemInfoHandle = 0;
-               
+               /* It's not an error if we don't find a buffer,
+                * we just return NULL */
                goto PVRSRV_BRIDGE_SGX_FINDSHAREDPBDESC_EXIT;
        }
 
@@ -2629,7 +2662,12 @@ SGXFindSharedPBDescBW(IMG_UINT32 ui32BridgeID,
                                          PVRSRV_HANDLE_TYPE_SHARED_PB_DESC,
                                          PVRSRV_HANDLE_ALLOC_FLAG_NONE);
 
-       
+       /*
+        * We allocate handles of type PVRSRV_HANDLE_TYPE_MEM_INFO_REF here,
+        * as the process doesn't own the underlying memory, and so should
+        * only be allowed a restricted set of operations on it, such as
+        * mapping it into its address space.
+        */
        PVRSRVAllocSubHandleNR(psPerProc->psHandleBase,
                                          &psSGXFindSharedPBDescOUT->hSharedPBDescKernelMemInfoHandle,
                                          psSharedPBDescKernelMemInfo,
@@ -2866,26 +2904,30 @@ SGXAddSharedPBDescBW(IMG_UINT32 ui32BridgeID,
                }
        }
 
-       
-        
+       /*
+        * Release all the handles we've just looked up, as none
+        * of the associated resources will be valid for access via
+        * those handles once we return from SGXAddSharedPBDesc.
+        */
+       /* PRQA S 3198 2 */ /* override redundant warning as PVR_ASSERT is ignored by QAC */
        eError = PVRSRVReleaseHandle(psPerProc->psHandleBase,
                                                                psSGXAddSharedPBDescIN->hSharedPBDescKernelMemInfo,
                                                                PVRSRV_HANDLE_TYPE_SHARED_SYS_MEM_INFO);
        PVR_ASSERT(eError == PVRSRV_OK);
 
-        
+       /* PRQA S 3198 2 */ /* override redundant warning as PVR_ASSERT is ignored by QAC */
        eError = PVRSRVReleaseHandle(psPerProc->psHandleBase,
                                                                psSGXAddSharedPBDescIN->hHWPBDescKernelMemInfo,
                                                                PVRSRV_HANDLE_TYPE_MEM_INFO);
        PVR_ASSERT(eError == PVRSRV_OK);
 
-        
+       /* PRQA S 3198 2 */ /* override redundant warning as PVR_ASSERT is ignored by QAC */
        eError = PVRSRVReleaseHandle(psPerProc->psHandleBase,
                                                                psSGXAddSharedPBDescIN->hBlockKernelMemInfo,
                                                                PVRSRV_HANDLE_TYPE_SHARED_SYS_MEM_INFO);
        PVR_ASSERT(eError == PVRSRV_OK);
 
-        
+       /* PRQA S 3198 2 */ /* override redundant warning as PVR_ASSERT is ignored by QAC */
        eError = PVRSRVReleaseHandle(psPerProc->psHandleBase,
                                                                psSGXAddSharedPBDescIN->hHWBlockKernelMemInfo,
                                                                PVRSRV_HANDLE_TYPE_MEM_INFO);
@@ -2893,7 +2935,7 @@ SGXAddSharedPBDescBW(IMG_UINT32 ui32BridgeID,
 
        for(i=0; i<ui32KernelMemInfoHandlesCount; i++)
        {
-                
+               /* PRQA S 3198 2 */ /* override redundant warning as PVR_ASSERT is ignored by QAC */
                eError = PVRSRVReleaseHandle(psPerProc->psHandleBase,
                                                                        phKernelMemInfoHandles[i],
                                                                        PVRSRV_HANDLE_TYPE_MEM_INFO);
@@ -3005,7 +3047,7 @@ SGXGetInfoForSrvinitBW(IMG_UINT32 ui32BridgeID,
                if ((asHeapInfo[i].ui32HeapID != (IMG_UINT32)SGX_UNDEFINED_HEAP_ID) &&
                        (asHeapInfo[i].hDevMemHeap != IMG_NULL))
                {
-                       
+                       /* Allocate heap handle */
                        PVRSRVAllocHandleNR(psPerProc->psHandleBase,
                                                          &psHeapInfo->hDevMemHeap,
                                                          asHeapInfo[i].hDevMemHeap,
@@ -3029,7 +3071,7 @@ SGXGetInfoForSrvinitBW(IMG_UINT32 ui32BridgeID,
 
                        if (psHeapInfo->hDevMemHeap != IMG_NULL)
                        {
-                               
+                               /* Allocate heap handle */
                                PVRSRVAllocHandleNR(psPerProc->psHandleBase,
                                                                  &hDevMemHeapExt,
                                                                  psHeapInfo->hDevMemHeap,
@@ -3047,6 +3089,13 @@ SGXGetInfoForSrvinitBW(IMG_UINT32 ui32BridgeID,
 }
 
 #if defined(PDUMP)
+// PRQA S 5120++
+/*****************************************************************************
+ FUNCTION      : DumpBufferArray
+ PURPOSE       : PDUMP information in stored buffer array
+ PARAMETERS    :
+ RETURNS       :
+*****************************************************************************/
 static IMG_VOID
 DumpBufferArray(PVRSRV_PER_PROCESS_DATA   *psPerProc,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -3114,7 +3163,9 @@ DumpBufferArray(PVRSRV_PER_PROCESS_DATA   *psPerProc,
                }
                else
                {
-                       
+                       /*
+                               Range of data wraps the end of the buffer so it needs to be dumped in two sections
+                       */
 
                        if (bDumpPolls)
                        {
@@ -3179,6 +3230,11 @@ SGXPDumpBufferArrayBW(IMG_UINT32 ui32BridgeID,
        SGX_KICKTA_DUMP_BUFFER *psUMPtr;
        SGX_KICKTA_DUMP_BUFFER_KM *psKickTADumpBufferKM, *psKMPtr;
 #else
+#if defined(__QNXNTO__)
+    const IMG_UINT32 NAME_BUFFER_SIZE = 30;
+    IMG_PCHAR pszNameBuffer, pszName;
+    IMG_UINT32 ui32NameBufferArraySize, ui32NameLength;
+#endif
        SGX_KICKTA_DUMP_BUFFER *psKickTADumpBuffer;
 #endif
        IMG_UINT32 ui32BufferArrayLength =
@@ -3187,12 +3243,6 @@ SGXPDumpBufferArrayBW(IMG_UINT32 ui32BridgeID,
                ui32BufferArrayLength * sizeof(SGX_KICKTA_DUMP_BUFFER);
        PVRSRV_ERROR eError = PVRSRV_ERROR_TOO_FEW_BUFFERS;
 
-#if defined (__QNXNTO__)
-    const IMG_UINT32 MAX_BUFFER_NAME_SIZE = 30;
-    IMG_PCHAR pszNamesBuffer, pszName;
-    IMG_UINT32 ui32NameBufferArraySize;
-#endif
-
        PVR_UNREFERENCED_PARAMETER(psBridgeOut);
 
        PVRSRV_BRIDGE_ASSERT_CMD(ui32BridgeID, PVRSRV_BRIDGE_SGX_PDUMP_BUFFER_ARRAY);
@@ -3220,38 +3270,48 @@ SGXPDumpBufferArrayBW(IMG_UINT32 ui32BridgeID,
                                                   ui32BufferArraySize) != PVRSRV_OK)
        {
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, ui32BufferArraySize, psKickTADumpBuffer, 0);
-               
+               /*not nulling pointer, out of scope*/
                return -EFAULT;
        }
-#endif
 
 #if defined (__QNXNTO__)
-    ui32NameBufferArraySize = ui32BufferArrayLength * MAX_BUFFER_NAME_SIZE;
+    ui32NameBufferArraySize = ui32BufferArrayLength * NAME_BUFFER_SIZE;
     if (OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP, ui32NameBufferArraySize,
-            (IMG_PVOID *)&pszNamesBuffer, 0,
+            (IMG_PVOID *)&pszNameBuffer, 0,
             "Kick Tile Accelerator Dump Buffer names") != PVRSRV_OK)
     {
         OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, ui32BufferArraySize, psKickTADumpBuffer, 0);
         return -ENOMEM;
     }
 
-    pszName = pszNamesBuffer;
+    pszName = pszNameBuffer;
+
     for (i=0; i<ui32BufferArrayLength; i++)
     {
-        if (CopyFromUserWrapper(psPerProc, ui32BridgeID, 
-                pszName, psKickTADumpBuffer[i].pszName,
-                MAX_BUFFER_NAME_SIZE) != PVRSRV_OK)
+        if (psKickTADumpBuffer[i].pszName)
         {
-            PVR_DPF((PVR_DBG_WARNING, "Failed to read pdump buffer name"));
-            psKickTADumpBuffer[i].pszName = 0;
+            ui32NameLength = psKickTADumpBuffer[i].ui32NameLength;
+            if (ui32NameLength >= NAME_BUFFER_SIZE)
+            {
+                ui32NameLength = NAME_BUFFER_SIZE - 1;
+            }
+
+            if (ui32NameLength && 
+                (CopyFromUserWrapper(psPerProc, ui32BridgeID, pszName, 
+                    psKickTADumpBuffer[i].pszName, ui32NameLength + 1) == PVRSRV_OK))
+            {
+                pszName[NAME_BUFFER_SIZE - 1] = 0;
+                psKickTADumpBuffer[i].pszName = pszName;
+                pszName += NAME_BUFFER_SIZE;
+            }
+            else 
+            {
+                PVR_DPF((PVR_DBG_WARNING, "Failed to read PDUMP buffer name"));
+                psKickTADumpBuffer[i].pszName = 0;
+            }
         }
-        else 
-        {
-            pszName[MAX_BUFFER_NAME_SIZE-1] = 0;
-            psKickTADumpBuffer[i].pszName = pszName;
-        }
-        pszName += MAX_BUFFER_NAME_SIZE;
     }
+#endif
 #endif
 
        for(i = 0; i < ui32BufferArrayLength; i++)
@@ -3337,12 +3397,11 @@ SGXPDumpBufferArrayBW(IMG_UINT32 ui32BridgeID,
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, ui32BufferArraySize, psKickTADumpBufferKM, 0);
 #else
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, ui32BufferArraySize, psKickTADumpBuffer, 0);
-#endif
-       
-
 #if defined (__QNXNTO__)
-       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, ui32NameBufferArraySize, pszNamesBuffer, 0);
+       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, ui32NameBufferArraySize, pszNameBuffer, 0);
 #endif
+#endif
+       /*not nulling pointer, out of scope*/
 
        return 0;
 }
@@ -3387,7 +3446,7 @@ SGXPDump3DSignatureRegistersBW(IMG_UINT32 ui32BridgeID,
        psDevInfo = (PVRSRV_SGXDEV_INFO*)psDeviceNode->pvDevice;
 
 #if defined(SGX_FEATURE_MP)    && defined(FIX_HW_BRN_27270)
-       
+       /* Enable all cores available */
        ui32RegVal = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_CORE);
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_CORE, (SGX_FEATURE_MP_CORE_COUNT - 1) << EUR_CR_MASTER_CORE_ENABLE_SHIFT);
 #if defined(PDUMP)
@@ -3431,8 +3490,8 @@ SGXPDump3DSignatureRegistersBW(IMG_UINT32 ui32BridgeID,
                return 0;
        }
 
-       
-       PVR_ASSERT(psDeviceNode->pfnMMUGetContextID != IMG_NULL)
+       /* look up the MMU context ID */
+       PVR_ASSERT(psDeviceNode->pfnMMUGetContextID != IMG_NULL);
        ui32MMUContextID = psDeviceNode->pfnMMUGetContextID((IMG_HANDLE)psDeviceNode->sDevMemoryInfo.pBMKernelContext);
 
        PDumpSignatureBuffer(&psDeviceNode->sDevId,
@@ -3440,13 +3499,13 @@ SGXPDump3DSignatureRegistersBW(IMG_UINT32 ui32BridgeID,
                                                 psDevInfo->psKernelTASigBufferMemInfo->sDevVAddr,
                                                 (IMG_UINT32)psDevInfo->psKernelTASigBufferMemInfo->uAllocSize,
                                                 ui32MMUContextID,
-                                                0 );
+                                                0 /*ui32PDumpFlags*/);
        PDumpSignatureBuffer(&psDeviceNode->sDevId,
                                                 "out.3dsig", "3D", 0,
                                                 psDevInfo->psKernel3DSigBufferMemInfo->sDevVAddr,
                                                 (IMG_UINT32)psDevInfo->psKernel3DSigBufferMemInfo->uAllocSize,
                                                 ui32MMUContextID,
-                                                0 );
+                                                0 /*ui32PDumpFlags*/);
 
 ExitNoError:
        psRetOUT->eError = PVRSRV_OK;
@@ -3576,7 +3635,7 @@ SGXPDumpTASignatureRegistersBW(IMG_UINT32 ui32BridgeID,
 
        psDevInfo = (PVRSRV_SGXDEV_INFO*)psDeviceNode->pvDevice;
 
-       
+       /* Enable all cores available */
        ui32RegVal = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_CORE);
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_CORE, (SGX_FEATURE_MP_CORE_COUNT - 1) << EUR_CR_MASTER_CORE_ENABLE_SHIFT);
 #if defined(PDUMP)
@@ -3634,6 +3693,9 @@ Exit:
 
        return ret;
 }
+//PRQA S 5120--
+
+
 static IMG_INT
 SGXPDumpHWPerfCBBW(IMG_UINT32                                          ui32BridgeID,
                                   PVRSRV_BRIDGE_IN_PDUMP_HWPERFCB      *psPDumpHWPerfCBIN,
@@ -3670,8 +3732,8 @@ SGXPDumpHWPerfCBBW(IMG_UINT32                                             ui32BridgeID,
                return 0;
        }
 
-       
-       PVR_ASSERT(psDeviceNode->pfnMMUGetContextID != IMG_NULL)
+       /* look up the MMU context ID */
+       PVR_ASSERT(psDeviceNode->pfnMMUGetContextID != IMG_NULL);
        ui32MMUContextID = psDeviceNode->pfnMMUGetContextID(hDevMemContextInt);
 
        PDumpHWPerfCBKM(&psDeviceNode->sDevId,
@@ -3689,14 +3751,14 @@ SGXPDumpHWPerfCBBW(IMG_UINT32                                           ui32BridgeID,
        PVR_UNREFERENCED_PARAMETER(psRetOUT);
        PVR_UNREFERENCED_PARAMETER(psPerProc);
        return 0;
-#endif 
+#endif /* defined(LINUX) || defined(UNDER_XP) */
 #else
        PVR_UNREFERENCED_PARAMETER(ui32BridgeID);
        PVR_UNREFERENCED_PARAMETER(psPDumpHWPerfCBIN);
        PVR_UNREFERENCED_PARAMETER(psRetOUT);
        PVR_UNREFERENCED_PARAMETER(psPerProc);
        return -EFAULT;
-#endif 
+#endif /* defined(SUPPORT_SGX_HWPERF) */
 }
 
 
@@ -3732,8 +3794,8 @@ SGXPDumpSaveMemBW(IMG_UINT32                                              ui32BridgeID,
                return 0;
        }
 
-       
-       PVR_ASSERT(psDeviceNode->pfnMMUGetContextID != IMG_NULL)
+       /* look up the MMU context ID */
+       PVR_ASSERT(psDeviceNode->pfnMMUGetContextID != IMG_NULL);
        ui32MMUContextID = psDeviceNode->pfnMMUGetContextID(hDevMemContextInt);
 
        PDumpSaveMemKM(&psDeviceNode->sDevId,
@@ -3746,10 +3808,10 @@ SGXPDumpSaveMemBW(IMG_UINT32                                            ui32BridgeID,
        return 0;
 }
 
-#endif 
+#endif /* PDUMP */
 
 
+/* PRQA S 0313,3635 END_SET_SGX */ /* function macro required this format */
 IMG_VOID SetSGXDispatchTableEntry(IMG_VOID)
 {
 
@@ -3798,6 +3860,6 @@ IMG_VOID SetSGXDispatchTableEntry(IMG_VOID)
        SetDispatchTableEntry(PVRSRV_BRIDGE_SGX_PDUMP_SAVEMEM, SGXPDumpSaveMemBW);
 #endif
 }
+/* PRQA L:END_SET_SGX */ /* end of setup overrides */
 
-#endif 
+#endif /* SUPPORT_SGX */
index 204450c..3cb6282 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX Bridge Functionality
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Header for the PVR Bridge code
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __BRIDGED_SGX_BRIDGE_H__
 #define __BRIDGED_SGX_BRIDGE_H__
@@ -38,5 +54,8 @@ IMG_VOID SetSGXDispatchTableEntry(IMG_VOID);
 }
 #endif
 
-#endif 
+#endif /* __BRIDGED_SGX_BRIDGE_H__ */
 
+/******************************************************************************
+ End of file (bridged_sgx_bridge.h)
+******************************************************************************/
index 96c28fb..8a459b1 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Buffer management functions for Linux
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Manages buffers mapped into two memory spaces - cpu and device,
+                either of which can be virtual or physical.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
 
@@ -38,8 +55,9 @@ static IMG_VOID
 BM_FreeMemory (IMG_VOID *pH, IMG_UINTPTR_T base, BM_MAPPING *psMapping);
 static IMG_BOOL
 BM_ImportMemory(IMG_VOID *pH, IMG_SIZE_T uSize,
-                                       IMG_SIZE_T *pActualSize, BM_MAPPING **ppsMapping,
-                                       IMG_UINT32 uFlags, IMG_UINTPTR_T *pBase);
+                               IMG_SIZE_T *pActualSize, BM_MAPPING **ppsMapping,
+                               IMG_UINT32 uFlags, IMG_PVOID pvPrivData,
+                               IMG_UINT32 ui32PrivDataLength, IMG_UINTPTR_T *pBase);
 
 static IMG_BOOL
 DevMemoryAlloc (BM_CONTEXT *pBMContext,
@@ -51,14 +69,53 @@ DevMemoryAlloc (BM_CONTEXT *pBMContext,
 static IMG_VOID
 DevMemoryFree (BM_MAPPING *pMapping);
 
+/*!
+******************************************************************************
+
+       @Function   AllocMemory
+
+       @Description    Allocate a buffer mapped into both cpu and device virtual
+                               address spaces.  This is now quite simple:
+
+                               1. Choose whence to get the memory;
+                               2. Obtain memory from that source;
+                               3. Work out the actual buffer addresses in other spaces.
+
+                               In choosing whence to get the memory we work like this:
+
+                               1. If an import arena exists, use unless BP_CONTIGUOUS is set;
+                               2. Use a contiguous pool.
+
+       @Input      pBMContext - BM context
+       @Input      psBMHeap - BM heap
+       @Input      psDevVAddr - device virtual address (optional)
+       @Input      uSize - requested buffer size in bytes.
+       @Input      uFlags - property flags for the buffer.
+    @Input      uDevVAddrAlignment - required device virtual address
+                                        alignment, or 0.
+    @Input      pvPrivData - opaque private data passed through to allocator
+    @Input      ui32PrivDataLength - length of opaque private data
+
+       @Output     pBuf - receives a pointer to a descriptor of the allocated
+                                        buffer.
+       @Return         IMG_TRUE - Success
+                               IMG_FALSE - Failed.
+
+ *****************************************************************************/
 static IMG_BOOL
-AllocMemory (BM_CONTEXT                                *pBMContext,
-                               BM_HEAP                         *psBMHeap,
-                               IMG_DEV_VIRTADDR        *psDevVAddr,
-                               IMG_SIZE_T                      uSize,
-                               IMG_UINT32                      uFlags,
-                               IMG_UINT32                      uDevVAddrAlignment,
-                               BM_BUF                          *pBuf)
+AllocMemory (BM_CONTEXT                        *pBMContext,
+                        BM_HEAP                        *psBMHeap,
+                        IMG_DEV_VIRTADDR       *psDevVAddr,
+                        IMG_SIZE_T                     uSize,
+                        IMG_UINT32                     uFlags,
+                        IMG_UINT32                     uDevVAddrAlignment,
+                        IMG_PVOID                      pvPrivData,
+                        IMG_UINT32                     ui32PrivDataLength,
+                        IMG_UINT32                     ui32ChunkSize,
+                        IMG_UINT32                     ui32NumVirtChunks,
+                        IMG_UINT32                     ui32NumPhysChunks,
+                        IMG_BOOL                       *pabMapChunk,
+                        BM_BUF                         *pBuf)
 {
        BM_MAPPING                      *pMapping;
        IMG_UINTPTR_T           uOffset;
@@ -68,26 +125,27 @@ AllocMemory (BM_CONTEXT                            *pBMContext,
                          "AllocMemory (uSize=0x%x, uFlags=0x%x, align=0x%x)",
                          uSize, uFlags, uDevVAddrAlignment));
 
-       
-
-
+       /*
+               what to do depends on combination of DevVaddr generation
+               and backing RAM requirement
+       */
        if(uFlags & PVRSRV_MEM_RAM_BACKED_ALLOCATION)
        {
                if(uFlags & PVRSRV_MEM_USER_SUPPLIED_DEVVADDR)
                {
-                       
+                       /* user supplied DevVAddr, RAM backing */
                        PVR_DPF ((PVR_DBG_ERROR, "AllocMemory: combination of DevVAddr management and RAM backing mode unsupported"));
                        return IMG_FALSE;
                }
 
-               
+               /* BM supplied DevVAddr, RAM Backing */
 
-               
+               /* check heap attributes */
                if(psBMHeap->ui32Attribs
                   &    (PVRSRV_BACKINGSTORE_SYSMEM_NONCONTIG
                   |PVRSRV_BACKINGSTORE_LOCALMEM_CONTIG))
                {
-                       
+                       /* specify arena (VM+RAM)*/
                        pArena = psBMHeap->pImportArena;
                        PVR_ASSERT(psBMHeap->sDevArena.psDeviceMemoryHeapInfo->ui32Attribs & PVRSRV_MEM_RAM_BACKED_ALLOCATION);
                }
@@ -97,18 +155,76 @@ AllocMemory (BM_CONTEXT                            *pBMContext,
                        return IMG_FALSE;
                }
 
+               /* Now allocate from the arena we chose above. */
+               if (uFlags & PVRSRV_MEM_SPARSE)
+               {
+                       IMG_BOOL bSuccess;
+                       IMG_SIZE_T puiActualSize;
+
+                       /* Allocate physcial memory */
+                       bSuccess = BM_ImportMemory(psBMHeap,
+                                                                          ui32ChunkSize * ui32NumPhysChunks,
+                                                                          &puiActualSize,
+                                                                          &pMapping,
+                                                                          uFlags,
+                                                                          pvPrivData,
+                                                                          ui32PrivDataLength,
+                                                                          IMG_NULL);   /* We allocate VM space */
+
+                       if (puiActualSize != ui32ChunkSize * ui32NumPhysChunks)
+                       {
+                               /*
+                                       Most likley the chunksize was not host page multiple so
+                                       return with an error
+                               */
+                               PVR_DPF((PVR_DBG_ERROR, "AllocMemory: Failed to allocate memory for sparse allocation"));
+                               BM_FreeMemory(pArena, IMG_NULL, pMapping);
+                               return IMG_FALSE;
+                       }
+
+                       pMapping->uSizeVM = ui32ChunkSize * ui32NumVirtChunks;
+                       uSize = pMapping->uSizeVM;
+                       pMapping->ui32ChunkSize = ui32ChunkSize;
+                       pMapping->ui32NumVirtChunks = ui32NumVirtChunks;
+                       pMapping->ui32NumPhysChunks = ui32NumPhysChunks;
+                       pMapping->pabMapChunk = pabMapChunk;
+
+                       /* Allocate VA space and map in the physical memory */
+                       bSuccess = DevMemoryAlloc (pBMContext,
+                                                                               pMapping,
+                                                                               IMG_NULL,
+                                                                               uFlags,
+                                                                               (IMG_UINT32)uDevVAddrAlignment,
+                                                                               &pMapping->DevVAddr);
+                       if (!bSuccess)
+                       {
+                               PVR_DPF((PVR_DBG_ERROR,
+                                               "AllocMemory: Failed to allocate device memory"));
+                               BM_FreeMemory(pArena, IMG_NULL, pMapping);
+                               return IMG_FALSE;
+                       }
                
-               if (!RA_Alloc(pArena,
-                                         uSize,
-                                         IMG_NULL,
-                                         (IMG_VOID*) &pMapping,
-                                         uFlags,
-                                         uDevVAddrAlignment,
-                                         0,
-                                         (IMG_UINTPTR_T *)&(pBuf->DevVAddr.uiAddr)))
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "AllocMemory: RA_Alloc(0x%x) FAILED", uSize));
-                       return IMG_FALSE;
+                       /* uDevVAddrAlignment is currently set to zero so QAC generates warning which we override */
+                       /* PRQA S 3356,3358 1 */
+                       PVR_ASSERT (uDevVAddrAlignment>1?(pMapping->DevVAddr.uiAddr%uDevVAddrAlignment)==0:1);
+                       pBuf->DevVAddr.uiAddr = pMapping->DevVAddr.uiAddr;
+               }
+               else
+               {
+                       if (!RA_Alloc(pArena,
+                                                 uSize,
+                                                 IMG_NULL,
+                                                 (IMG_VOID*) &pMapping,
+                                                 uFlags,
+                                                 uDevVAddrAlignment,
+                                                 0,
+                                                 pvPrivData,
+                                                 ui32PrivDataLength,
+                                                 (IMG_UINTPTR_T *)&(pBuf->DevVAddr.uiAddr)))
+                       {
+                               PVR_DPF((PVR_DBG_ERROR, "AllocMemory: RA_Alloc(0x%x) FAILED", uSize));
+                               return IMG_FALSE;
+                       }
                }
 
                uOffset = pBuf->DevVAddr.uiAddr - pMapping->DevVAddr.uiAddr;
@@ -121,7 +237,7 @@ AllocMemory (BM_CONTEXT                             *pBMContext,
                        pBuf->CpuVAddr = IMG_NULL;
                }
 
-               if(uSize == pMapping->uSize)
+               if(uSize == pMapping->uSizeVM)
                {
                        pBuf->hOSMemHandle = pMapping->hOSMemHandle;
                }
@@ -138,7 +254,8 @@ AllocMemory (BM_CONTEXT                             *pBMContext,
                        }
                }
 
-               
+               /* for hm_contiguous and hm_wrapped memory, the pMapping
+                * will have a physical address, else 0 */
                pBuf->CpuPAddr.uiAddr = pMapping->CpuPAddr.uiAddr + uOffset;
 
                if(uFlags & PVRSRV_MEM_ZERO)
@@ -153,7 +270,7 @@ AllocMemory (BM_CONTEXT                             *pBMContext,
        {
                if(uFlags & PVRSRV_MEM_USER_SUPPLIED_DEVVADDR)
                {
-                       
+                       /* user supplied DevVAddr, no RAM backing */
                        PVR_ASSERT(psDevVAddr != IMG_NULL);
 
                        if (psDevVAddr == IMG_NULL)
@@ -162,7 +279,7 @@ AllocMemory (BM_CONTEXT                             *pBMContext,
                                return IMG_FALSE;
                        }
 
-                       
+                       /* just make space in the pagetables */
                        pBMContext->psDeviceNode->pfnMMUAlloc (psBMHeap->pMMUHeap,
                                                                                                        uSize,
                                                                                                        IMG_NULL,
@@ -170,23 +287,30 @@ AllocMemory (BM_CONTEXT                           *pBMContext,
                                                                                                        uDevVAddrAlignment,
                                                                                                        psDevVAddr);
 
-                       
+                       /* setup buf */
                        pBuf->DevVAddr = *psDevVAddr;
                }
                else
                {
-                       
+                       IMG_BOOL bResult;
+                       /* BM supplied DevVAddr, no RAM Backing */
 
-                       
-                       pBMContext->psDeviceNode->pfnMMUAlloc (psBMHeap->pMMUHeap,
+                       /* just make space in the pagetables */
+                       bResult = pBMContext->psDeviceNode->pfnMMUAlloc (psBMHeap->pMMUHeap,
                                                                                                        uSize,
                                                                                                        IMG_NULL,
                                                                                                        0,
                                                                                                        uDevVAddrAlignment,
                                                                                                        &pBuf->DevVAddr);
+
+                       if(!bResult)
+                       {
+                               PVR_DPF((PVR_DBG_ERROR, "AllocMemory: MMUAlloc failed"));
+                               return IMG_FALSE;
+                       }
                }
 
-               
+               /* allocate a mocked-up mapping */
                if (OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                                        sizeof (struct _BM_MAPPING_),
                                                        (IMG_PVOID *)&pMapping, IMG_NULL,
@@ -196,12 +320,12 @@ AllocMemory (BM_CONTEXT                           *pBMContext,
                        return IMG_FALSE;
                }
 
-               
+               /* setup buf */
                pBuf->CpuVAddr = IMG_NULL;
                pBuf->hOSMemHandle = 0;
                pBuf->CpuPAddr.uiAddr = 0;
 
-               
+               /* setup mapping */
                pMapping->CpuVAddr = IMG_NULL;
                pMapping->CpuPAddr.uiAddr = 0;
                pMapping->DevVAddr = pBuf->DevVAddr;
@@ -210,14 +334,14 @@ AllocMemory (BM_CONTEXT                           *pBMContext,
                pMapping->hOSMemHandle = 0;
        }
 
-       
+       /* Record the arena pointer in the mapping. */
        pMapping->pArena = pArena;
 
-       
+       /* record the heap */
        pMapping->pBMHeap = psBMHeap;
        pBuf->pMapping = pMapping;
 
-       
+       /* output some stats */
        PVR_DPF ((PVR_DBG_MESSAGE,
                                "AllocMemory: pMapping=%08x: DevV=%08X CpuV=%08x CpuP=%08X uSize=0x%x",
                                (IMG_UINTPTR_T)pMapping,
@@ -234,13 +358,34 @@ AllocMemory (BM_CONTEXT                           *pBMContext,
                                pBuf->CpuPAddr.uiAddr,
                                uSize));
 
-       
+       /* Verify virtual device address alignment */
        PVR_ASSERT(((pBuf->DevVAddr.uiAddr) & (uDevVAddrAlignment - 1)) == 0);
 
        return IMG_TRUE;
 }
 
 
+/*!
+******************************************************************************
+
+       @Function       WrapMemory
+
+       @Description Allocate a buffer mapped into both cpu and device virtual
+                               address spaces.
+
+       @Input      psBMHeap - BM heap
+       @Input      uSize - requested buffer size in bytes.
+       @Input      ui32BaseOffset - Offset from page of wrap.
+       @Input      bPhysContig - Is the wrap physically contiguous.
+       @Input      psAddr - List of pages to wrap.
+       @Input      pvCPUVAddr - Optional CPU Kernel virtual address (page aligned) of memory to wrap
+       @Input      uFlags - property flags for the buffer.
+       @Output     Buf - receives a pointer to a descriptor of the allocated
+                                        buffer.
+       @Return         IMG_TRUE - Success
+                               IMG_FALSE - Failed.
+
+ *****************************************************************************/
 static IMG_BOOL
 WrapMemory (BM_HEAP *psBMHeap,
                        IMG_SIZE_T uSize,
@@ -261,13 +406,13 @@ WrapMemory (BM_HEAP *psBMHeap,
                          (IMG_UINTPTR_T)psBMHeap, uSize, ui32BaseOffset, bPhysContig, (IMG_UINTPTR_T)pvCPUVAddr, uFlags));
 
        PVR_ASSERT((psAddr->uiAddr & (ui32PageSize - 1)) == 0);
-       
+       /* Only need lower 12 bits of the cpu addr - don't care what size a void* is */
        PVR_ASSERT(((IMG_UINTPTR_T)pvCPUVAddr & (ui32PageSize - 1)) == 0);
 
        uSize += ui32BaseOffset;
        uSize = HOST_PAGEALIGN (uSize);
 
-       
+       /* allocate a mocked-up mapping */
        if (OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                                sizeof(*pMapping),
                                                (IMG_PVOID *)&pMapping, IMG_NULL,
@@ -280,6 +425,7 @@ WrapMemory (BM_HEAP *psBMHeap,
        OSMemSet(pMapping, 0, sizeof (*pMapping));
 
        pMapping->uSize = uSize;
+       pMapping->uSizeVM = uSize;
        pMapping->pBMHeap = psBMHeap;
 
        if(pvCPUVAddr)
@@ -329,6 +475,7 @@ WrapMemory (BM_HEAP *psBMHeap,
                        if(OSReservePhys(pMapping->CpuPAddr,
                                                         pMapping->uSize,
                                                         uFlags,
+                                                        IMG_NULL,
                                                         &pMapping->CpuVAddr,
                                                         &pMapping->hOSMemHandle) != PVRSRV_OK)
                        {
@@ -355,7 +502,9 @@ WrapMemory (BM_HEAP *psBMHeap,
                }
        }
 
-       
+       /*
+        * Allocate device memory for this buffer. Map wrapped pages as read/write
+        */
        bResult = DevMemoryAlloc(psBMHeap->pBMContext,
                                                         pMapping,
                                                         IMG_NULL,
@@ -370,7 +519,12 @@ WrapMemory (BM_HEAP *psBMHeap,
                goto fail_cleanup;
        }
 
-       
+       /*
+        * Determine the offset of this allocation within the underlying
+        * dual mapped chunk of memory, we can assume that all three
+        * addresses associated with this allocation are placed at the same
+        * offset within the underlying chunk.
+        */
        pBuf->CpuPAddr.uiAddr = pMapping->CpuPAddr.uiAddr + ui32BaseOffset;
        if(!ui32BaseOffset)
        {
@@ -442,7 +596,7 @@ fail_cleanup:
        }
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_MAPPING), pMapping, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
 
        return IMG_FALSE;
 }
@@ -483,14 +637,18 @@ ZeroBuf(BM_BUF *pBuf, BM_MAPPING *pMapping, IMG_SIZE_T ui32Bytes, IMG_UINT32 ui3
                IMG_SIZE_T ui32CurrentOffset = 0;
                IMG_CPU_PHYADDR CpuPAddr;
 
-               
+               /* Walk through the pBuf one page at a time and use
+                * transient mappings to zero the memory */
+
                PVR_ASSERT(pBuf->hOSMemHandle);
 
                while(ui32BytesRemaining > 0)
                {
                        IMG_SIZE_T ui32BlockBytes = MIN(ui32BytesRemaining, HOST_PAGESIZE());
                        CpuPAddr = OSMemHandleToCpuPAddr(pBuf->hOSMemHandle, ui32CurrentOffset);
-                       
+                       /* If the CpuPAddr isn't page aligned then start by writing up to the next page
+                        * boundary (or ui32BytesRemaining if less), so that subsequent iterations can
+                        * copy full physical pages. */
                        if(CpuPAddr.uiAddr & (HOST_PAGESIZE() -1))
                        {
                                ui32BlockBytes =
@@ -522,6 +680,26 @@ ZeroBuf(BM_BUF *pBuf, BM_MAPPING *pMapping, IMG_SIZE_T ui32Bytes, IMG_UINT32 ui3
        return IMG_TRUE;
 }
 
+/*!
+******************************************************************************
+
+       @Function       FreeBuf
+
+       @Description    Free a buffer previously allocated with BM_Alloc() or unwrap
+                               one previous wrapped with BM_Wrap().
+                               The buffer is identified by the buffer descriptor pBuf
+                               returned at allocation. Note the double indirection when
+                               passing the buffer.
+
+       
+       @Input      pBuf - buffer descriptor to free.
+       @Input      ui32Flags - flags
+       @Input      bFromAllocator - Is this being called by the
+                                                        allocator?
+
+       @Return         None.
+
+ *****************************************************************************/
 static IMG_VOID
 FreeBuf (BM_BUF *pBuf, IMG_UINT32 ui32Flags, IMG_BOOL bFromAllocator)
 {
@@ -533,7 +711,7 @@ FreeBuf (BM_BUF *pBuf, IMG_UINT32 ui32Flags, IMG_BOOL bFromAllocator)
                        (IMG_UINTPTR_T)pBuf, pBuf->DevVAddr.uiAddr,
                        (IMG_UINTPTR_T)pBuf->CpuVAddr, pBuf->CpuPAddr.uiAddr));
 
-       
+       /* record mapping */
        pMapping = pBuf->pMapping;
 
        psDeviceNode = pMapping->pBMHeap->pBMContext->psDeviceNode;
@@ -544,46 +722,60 @@ FreeBuf (BM_BUF *pBuf, IMG_UINT32 ui32Flags, IMG_BOOL bFromAllocator)
 
        if(ui32Flags & PVRSRV_MEM_USER_SUPPLIED_DEVVADDR)
        {
-               
+               /* Submemhandle is required by exported mappings */
                if ((pBuf->ui32ExportCount == 0) && (pBuf->ui32RefCount == 0))
                {
-                       
+                       /* user supplied Device Virtual Address */
                        if(ui32Flags & PVRSRV_MEM_RAM_BACKED_ALLOCATION)
                        {
-                               
+                               /* RAM backed allocation */
                                PVR_DPF ((PVR_DBG_ERROR, "FreeBuf: combination of DevVAddr management and RAM backing mode unsupported"));
                        }
                        else
                        {
-                               
+                               /* free the mocked-up mapping */
                                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_MAPPING), pMapping, IMG_NULL);
-                               pBuf->pMapping = IMG_NULL; 
+                               pBuf->pMapping = IMG_NULL; /*nulling pointer alias*/
                        }
                }
        }
        else
        {
-               
+               /* BM supplied Device Virtual Address */
                if(pBuf->hOSMemHandle != pMapping->hOSMemHandle)
                {
-            
+                       /* Submemhandle is required by exported mappings */
                        if ((pBuf->ui32ExportCount == 0) && (pBuf->ui32RefCount == 0))
                        {
-                               
                                OSReleaseSubMemHandle(pBuf->hOSMemHandle, ui32Flags);
                        }
                }
                if(ui32Flags & PVRSRV_MEM_RAM_BACKED_ALLOCATION)
                {
-                       
-            
+                       /* Submemhandle is required by exported mappings */
                        if ((pBuf->ui32ExportCount == 0) && (pBuf->ui32RefCount == 0))
                        {
-                               
-
-
-                               PVR_ASSERT(pBuf->ui32ExportCount == 0)
-                               RA_Free (pBuf->pMapping->pArena, pBuf->DevVAddr.uiAddr, IMG_FALSE);
+                               /*
+                                       RAM backed allocation
+                                       Note: currently no need to distinguish between hm_env and hm_contiguous
+                               */
+                               PVR_ASSERT(pBuf->ui32ExportCount == 0);
+                               if (pBuf->pMapping->ui32Flags & PVRSRV_MEM_SPARSE)
+                               {
+                                       IMG_UINT32 ui32FreeSize = sizeof(IMG_BOOL) * pBuf->pMapping->ui32NumVirtChunks;
+                                       IMG_PVOID pvFreePtr = pBuf->pMapping->pabMapChunk;
+                                       
+                                       /* With sparse allocations we don't go through the sub-alloc RA */
+                                       BM_FreeMemory(pBuf->pMapping->pBMHeap, pBuf->DevVAddr.uiAddr, pBuf->pMapping);
+                                       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                                         ui32FreeSize,
+                                                         pvFreePtr,
+                                                         IMG_NULL);
+                               }
+                               else
+                               {
+                                       RA_Free (pBuf->pMapping->pArena, pBuf->DevVAddr.uiAddr, IMG_FALSE);
+                               }
                        }
                }
                else
@@ -613,9 +805,9 @@ FreeBuf (BM_BUF *pBuf, IMG_UINT32 ui32Flags, IMG_BOOL bFromAllocator)
 
                        if ((pBuf->ui32ExportCount == 0) && (pBuf->ui32RefCount == 0))
                        {
-                               
+                               /* free the mocked-up mapping */
                                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_MAPPING), pMapping, IMG_NULL);
-                               pBuf->pMapping = IMG_NULL; 
+                               pBuf->pMapping = IMG_NULL; /*nulling pointer alias*/
                        }
                }
        }
@@ -624,10 +816,22 @@ FreeBuf (BM_BUF *pBuf, IMG_UINT32 ui32Flags, IMG_BOOL bFromAllocator)
        if ((pBuf->ui32ExportCount == 0) && (pBuf->ui32RefCount == 0))
        {
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_BUF), pBuf, IMG_NULL);
-               
+               /*not nulling pointer, copy on stack*/
        }
 }
 
+/*!
+******************************************************************************
+
+       @Function       BM_DestroyContext_AnyCb
+
+       @Description    Destroy a buffer manager heap.
+
+       @Input      psBMHeap
+
+       @Return         PVRSRV_ERROR
+
+ *****************************************************************************/
 static PVRSRV_ERROR BM_DestroyContext_AnyCb(BM_HEAP *psBMHeap)
 {
        if(psBMHeap->ui32Attribs
@@ -648,6 +852,20 @@ static PVRSRV_ERROR BM_DestroyContext_AnyCb(BM_HEAP *psBMHeap)
 }
 
 
+/*!
+******************************************************************************
+
+       @Function       BM_DestroyContext
+
+       @Description    Destroy a buffer manager context. All allocated buffers must be
+                               free'd before calling this function.  This function is called
+                               also to perform cleanup during aborted initialisations so it's
+                               fairly careful not to assume any given resource has really been
+                               created/allocated.
+
+       @Return         PVRSRV_ERROR
+
+ *****************************************************************************/
 PVRSRV_ERROR
 BM_DestroyContext(IMG_HANDLE   hBMContext,
                                  IMG_BOOL              *pbDestroyed)
@@ -662,8 +880,9 @@ BM_DestroyContext(IMG_HANDLE        hBMContext,
                *pbDestroyed = IMG_FALSE;
        }
 
-       
-
+       /*
+               Exit straight away if it's an invalid context handle
+       */
        if (pBMContext == IMG_NULL)
        {
                PVR_DPF ((PVR_DBG_ERROR, "BM_DestroyContext: Invalid handle"));
@@ -674,34 +893,23 @@ BM_DestroyContext(IMG_HANDLE      hBMContext,
 
        if (pBMContext->ui32RefCount > 0)
        {
-               
+               /* Just return if there are more references to this context */
                return PVRSRV_OK;
        }
 
-       
-
-
+       /*
+               Check whether there is a bug in the client which brought it here before
+               all the allocations have been freed.
+       */
        eError = List_BM_HEAP_PVRSRV_ERROR_Any(pBMContext->psBMHeap, &BM_DestroyContext_AnyCb);
        if(eError != PVRSRV_OK)
        {
                PVR_DPF ((PVR_DBG_ERROR, "BM_DestroyContext: List_BM_HEAP_PVRSRV_ERROR_Any failed"));
-#if 0
-               
-               
-               
-               
-               PVR_DPF ((PVR_DBG_ERROR, "BM_DestroyContext: Cleaning up with ResManFreeSpecial"));
-               if(ResManFreeSpecial() != PVRSRV_OK)
-               {
-                       PVR_DPF ((PVR_DBG_ERROR, "BM_DestroyContext: ResManFreeSpecial failed %d",eError));
-               }
-               
-#endif
                return eError;
        }
        else
        {
-               
+               /* free the device memory context */
                eError = ResManFreeResByPtr(pBMContext->hResItem, CLEANUP_WITH_POLL);
                if(eError != PVRSRV_OK)
                {
@@ -709,7 +917,7 @@ BM_DestroyContext(IMG_HANDLE        hBMContext,
                        return eError;
                }
 
-               
+               /* mark context as destroyed */
                if (pbDestroyed != IMG_NULL)
                {
                        *pbDestroyed = IMG_TRUE;
@@ -720,12 +928,25 @@ BM_DestroyContext(IMG_HANDLE      hBMContext,
 }
 
 
+/*!
+******************************************************************************
+
+       @Function       BM_DestroyContextCallBack_AnyVaCb
+
+       @Description    Destroy Device memory context
+
+       @Input      psBMHeap - heap to be freed.
+    @Input      va - list of variable arguments with the following contents:
+                                       - psDeviceNode
+       @Return         PVRSRV_ERROR
+
+ *****************************************************************************/
 static PVRSRV_ERROR BM_DestroyContextCallBack_AnyVaCb(BM_HEAP *psBMHeap, va_list va)
 {
        PVRSRV_DEVICE_NODE *psDeviceNode;
        psDeviceNode = va_arg(va, PVRSRV_DEVICE_NODE*);
 
-       
+       /* Free up the import arenas */
        if(psBMHeap->ui32Attribs
        &       (PVRSRV_BACKINGSTORE_SYSMEM_NONCONTIG
                |PVRSRV_BACKINGSTORE_LOCALMEM_CONTIG))
@@ -741,17 +962,30 @@ static PVRSRV_ERROR BM_DestroyContextCallBack_AnyVaCb(BM_HEAP *psBMHeap, va_list
                return PVRSRV_ERROR_UNSUPPORTED_BACKING_STORE;
        }
 
-       
+       /* Free up the MMU Heaps */
        psDeviceNode->pfnMMUDelete(psBMHeap->pMMUHeap);
 
-       
+       /* Free Heap memory */
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_HEAP), psBMHeap, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+       @Function       BM_DestroyContextCallBack
+
+       @Description    Destroy Device memory context
+
+       @Input      pvParam - opaque void ptr param
+    @Input      ui32Param - opaque unsigned long param
+
+       @Return         PVRSRV_ERROR
+
+ *****************************************************************************/
 static PVRSRV_ERROR BM_DestroyContextCallBack(IMG_PVOID   pvParam,
                                                                                          IMG_UINT32  ui32Param,
                                                                                          IMG_BOOL    bDummy)
@@ -759,15 +993,20 @@ static PVRSRV_ERROR BM_DestroyContextCallBack(IMG_PVOID   pvParam,
        BM_CONTEXT *pBMContext = pvParam;
        PVRSRV_DEVICE_NODE *psDeviceNode;
        PVRSRV_ERROR eError;
+/*     BM_CONTEXT **ppBMContext;
+       BM_HEAP *psBMHeap, *psTmpBMHeap;*/
+
        PVR_UNREFERENCED_PARAMETER(ui32Param);
        PVR_UNREFERENCED_PARAMETER(bDummy);
 
-       
-
+       /*
+               Get DeviceNode from BMcontext
+       */
        psDeviceNode = pBMContext->psDeviceNode;
 
-       
-
+       /*
+               Free the import arenas and heaps
+       */
        eError = List_BM_HEAP_PVRSRV_ERROR_Any_va(pBMContext->psBMHeap,
                                                                                &BM_DestroyContextCallBack_AnyVaCb,
                                                                                psDeviceNode);
@@ -775,15 +1014,17 @@ static PVRSRV_ERROR BM_DestroyContextCallBack(IMG_PVOID   pvParam,
        {
                return eError;
        }
-       
-
+       /*
+               'Finalise' the MMU
+       */
        if (pBMContext->psMMUContext)
        {
                psDeviceNode->pfnMMUFinalise(pBMContext->psMMUContext);
        }
 
-       
-
+       /*
+               Free up generic, useful resources - if they were allocated.
+       */
        if (pBMContext->pBufferHash)
        {
                HASH_Delete(pBMContext->pBufferHash);
@@ -791,20 +1032,22 @@ static PVRSRV_ERROR BM_DestroyContextCallBack(IMG_PVOID   pvParam,
 
        if (pBMContext == psDeviceNode->sDevMemoryInfo.pBMKernelContext)
        {
-               
+               /* Freeing the kernel context */
                psDeviceNode->sDevMemoryInfo.pBMKernelContext = IMG_NULL;
        }
        else
        {
            if (pBMContext->ppsThis != IMG_NULL)
            {
-                   
+                   /*
+                    * Remove context from the linked list
+                    */
                    List_BM_CONTEXT_Remove(pBMContext);
                }
        }
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_CONTEXT), pBMContext, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        return PVRSRV_OK;
 }
@@ -816,7 +1059,7 @@ static IMG_HANDLE BM_CreateContext_IncRefCount_AnyVaCb(BM_CONTEXT *pBMContext, v
        hResManContext = va_arg(va, PRESMAN_CONTEXT);
        if(ResManFindResourceByPtr(hResManContext, pBMContext->hResItem) == PVRSRV_OK)
        {
-               
+               /* just increment the refcount and return the memory context found for this process */
                pBMContext->ui32RefCount++;
                return pBMContext;
        }
@@ -834,13 +1077,25 @@ static IMG_VOID BM_CreateContext_InsertHeap_ForEachVaCb(BM_HEAP *psBMHeap, va_li
                case DEVICE_MEMORY_HEAP_SHARED:
                case DEVICE_MEMORY_HEAP_SHARED_EXPORTED:
                {
-                       
+                       /* insert the heap into the device's MMU page directory/table */
                        psDeviceNode->pfnMMUInsertHeap(pBMContext->psMMUContext, psBMHeap->pMMUHeap);
                        break;
                }
        }
 }
 
+/*!
+******************************************************************************
+
+       @Function       BM_CreateContext
+
+       @Description    Creates and initialises a buffer manager context. This function must be called
+                               before any other buffer manager functions.
+
+       @Return         valid BM context handle - Success
+                               IMG_NULL - Failed
+
+ *****************************************************************************/
 IMG_HANDLE
 BM_CreateContext(PVRSRV_DEVICE_NODE                    *psDeviceNode,
                                 IMG_DEV_PHYADDR                        *psPDDevPAddr,
@@ -848,6 +1103,7 @@ BM_CreateContext(PVRSRV_DEVICE_NODE                        *psDeviceNode,
                                 IMG_BOOL                                       *pbCreated)
 {
        BM_CONTEXT                      *pBMContext;
+/*     BM_HEAP                         *psBMHeap;*/
        DEVICE_MEMORY_INFO      *psDevMemoryInfo;
        IMG_BOOL                        bKernelContext;
        PRESMAN_CONTEXT         hResManContext;
@@ -870,7 +1126,7 @@ BM_CreateContext(PVRSRV_DEVICE_NODE                        *psDeviceNode,
                *pbCreated = IMG_FALSE;
        }
 
-       
+       /* setup the device memory info. */
        psDevMemoryInfo = &psDeviceNode->sDevMemoryInfo;
 
        if (bKernelContext == IMG_FALSE)
@@ -884,7 +1140,7 @@ BM_CreateContext(PVRSRV_DEVICE_NODE                        *psDeviceNode,
                }
        }
 
-       
+       /* allocate a BM context */
        if (OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                         sizeof (struct _BM_CONTEXT_),
                                         (IMG_PVOID *)&pBMContext, IMG_NULL,
@@ -895,11 +1151,11 @@ BM_CreateContext(PVRSRV_DEVICE_NODE                      *psDeviceNode,
        }
        OSMemSet(pBMContext, 0, sizeof (BM_CONTEXT));
 
-       
+       /* store the associated devicenode */
        pBMContext->psDeviceNode = psDeviceNode;
 
-       
-       
+       /* This hash table is used to store BM_Wraps in a global way */
+       /* INTEGRATION_POINT: 32 is an abitrary limit on the number of hashed BM_wraps */
        pBMContext->pBufferHash = HASH_Create(32);
        if (pBMContext->pBufferHash==IMG_NULL)
        {
@@ -917,17 +1173,18 @@ BM_CreateContext(PVRSRV_DEVICE_NODE                      *psDeviceNode,
 
        if(bKernelContext)
        {
-               
+               /* just save the kernel context  */
                PVR_ASSERT(psDevMemoryInfo->pBMKernelContext == IMG_NULL);
                psDevMemoryInfo->pBMKernelContext = pBMContext;
        }
        else
        {
-               
-
-
-
-
+               /*
+                       On the creation of each new context we must
+                       insert the kernel context's 'shared' and 'shared_exported'
+                       heaps into the new context
+                        - check the kernel context and heaps exist
+               */
                PVR_ASSERT(psDevMemoryInfo->pBMKernelContext);
 
                if (psDevMemoryInfo->pBMKernelContext == IMG_NULL)
@@ -938,28 +1195,30 @@ BM_CreateContext(PVRSRV_DEVICE_NODE                      *psDeviceNode,
 
                PVR_ASSERT(psDevMemoryInfo->pBMKernelContext->psBMHeap);
 
-               
-
-
-
+               /*
+                       insert the kernel heaps structures into the new context's shared heap list
+                       Note. this will include the kernel only heaps but these will not actually
+                       be imported into the context nor returned to the client
+                */
                pBMContext->psBMSharedHeap = psDevMemoryInfo->pBMKernelContext->psBMHeap;
 
-               
-
-
+               /*
+                       insert the shared heaps into the MMU page directory/table
+                       for the new context
+               */
                List_BM_HEAP_ForEach_va(pBMContext->psBMSharedHeap,
                                                                &BM_CreateContext_InsertHeap_ForEachVaCb,
                                                                psDeviceNode,
                                                                pBMContext);
 
-               
+               /* Finally, insert the new context into the list of BM contexts */
                List_BM_CONTEXT_Insert(&psDevMemoryInfo->pBMContext, pBMContext);
        }
 
-       
+       /* Increment the refcount, as creation is successful */
        pBMContext->ui32RefCount++;
 
-       
+       /* register with resman */
        pBMContext->hResItem = ResManRegisterRes(hResManContext,
                                                                                        RESMAN_TYPE_DEVICEMEM_CONTEXT,
                                                                                        pBMContext,
@@ -990,7 +1249,7 @@ static IMG_VOID *BM_CreateHeap_AnyVaCb(BM_HEAP *psBMHeap, va_list va)
        psDevMemHeapInfo = va_arg(va, DEVICE_MEMORY_HEAP_INFO*);
        if (psBMHeap->sDevArena.ui32HeapID ==  psDevMemHeapInfo->ui32HeapID)
        {
-               
+               /* Match - just return already created heap */
                return psBMHeap;
        }
        else
@@ -999,6 +1258,19 @@ static IMG_VOID *BM_CreateHeap_AnyVaCb(BM_HEAP *psBMHeap, va_list va)
        }
 }
 
+/*!
+******************************************************************************
+
+       @Function       BM_CreateHeap
+
+       @Description    Creates and initialises a BM heap for a given BM context.
+
+       @Return 
+               valid heap handle - success
+               IMG_NULL - failure
+
+
+ *****************************************************************************/
 IMG_HANDLE
 BM_CreateHeap (IMG_HANDLE hBMContext,
                           DEVICE_MEMORY_HEAP_INFO *psDevMemHeapInfo)
@@ -1017,16 +1289,18 @@ BM_CreateHeap (IMG_HANDLE hBMContext,
 
        psDeviceNode = pBMContext->psDeviceNode;
 
-       
+       /*
+        * Ensure that the heap size is a multiple of the data page size.
+        */ 
        PVR_ASSERT((psDevMemHeapInfo->ui32HeapSize & (psDevMemHeapInfo->ui32DataPageSize - 1)) == 0);
        PVR_ASSERT(psDevMemHeapInfo->ui32HeapSize > 0);
 
-       
-
-
-
-
+       /*
+               We may be being asked to create a heap in a context which already has one.
+               Test for refcount > 0 because PVRSRVGetDeviceMemHeapInfoKM doesn't increment the refcount.
+               This does mean that the first call to PVRSRVCreateDeviceMemContextKM will first try to find
+               heaps that we already know don't exist
+       */
        if(pBMContext->ui32RefCount > 0)
        {
                psBMHeap = (BM_HEAP*)List_BM_HEAP_Any_va(pBMContext->psBMHeap,
@@ -1059,8 +1333,11 @@ BM_CreateHeap (IMG_HANDLE hBMContext,
        psBMHeap->sDevArena.ui32DataPageSize = psDevMemHeapInfo->ui32DataPageSize;
        psBMHeap->sDevArena.psDeviceMemoryHeapInfo = psDevMemHeapInfo;
        psBMHeap->ui32Attribs = psDevMemHeapInfo->ui32Attribs;
+#if defined(SUPPORT_MEMORY_TILING)
+       psBMHeap->ui32XTileStride = psDevMemHeapInfo->ui32XTileStride;
+#endif
 
-       
+       /* tie the heap to the context */
        psBMHeap->pBMContext = pBMContext;
 
        psBMHeap->pMMUHeap = psDeviceNode->pfnMMUCreate (pBMContext->psMMUContext,
@@ -1073,7 +1350,7 @@ BM_CreateHeap (IMG_HANDLE hBMContext,
                goto ErrorExit;
        }
 
-       
+       /* memory is allocated from the OS as required */
        psBMHeap->pImportArena = RA_Create (psDevMemHeapInfo->pszBSName,
                                                                                0, 0, IMG_NULL,
                                                                                MAX(HOST_PAGESIZE(), psBMHeap->sDevArena.ui32DataPageSize),
@@ -1089,10 +1366,11 @@ BM_CreateHeap (IMG_HANDLE hBMContext,
 
        if(psBMHeap->ui32Attribs & PVRSRV_BACKINGSTORE_LOCALMEM_CONTIG)
        {
-               
-
-
-
+               /*
+                       memory comes from a device memory contiguous allocator (ra)
+                       Note: these arenas are shared across the system so don't delete
+                       as part of heap destroy
+               */
                psBMHeap->pLocalDevMemArena = psDevMemHeapInfo->psLocalDevMemArena;
                if(psBMHeap->pLocalDevMemArena == IMG_NULL)
                {
@@ -1101,28 +1379,41 @@ BM_CreateHeap (IMG_HANDLE hBMContext,
                }
        }
 
-       
+       /* insert heap into head of the heap list */
        List_BM_HEAP_Insert(&pBMContext->psBMHeap, psBMHeap);
 
        return (IMG_HANDLE)psBMHeap;
 
-       
+       /* handle error case */
 ErrorExit:
 
-       
+       /* Free up the MMU if we created one */
        if (psBMHeap->pMMUHeap != IMG_NULL)
        {
                psDeviceNode->pfnMMUDelete (psBMHeap->pMMUHeap);
-               
+               /* don't finalise psMMUContext as we don't own it */
        }
 
-       
+       /* Free the Heap memory */
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_HEAP), psBMHeap, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
 
        return IMG_NULL;
 }
 
+/*!
+******************************************************************************
+
+       @Function       BM_DestroyHeap
+
+       @Description    Destroys a BM heap
+
+       @Return 
+               valid heap handle - success
+               IMG_NULL - failure
+
+
+ *****************************************************************************/
 IMG_VOID
 BM_DestroyHeap (IMG_HANDLE hDevMemHeap)
 {
@@ -1133,7 +1424,7 @@ BM_DestroyHeap (IMG_HANDLE hDevMemHeap)
 
        if(psBMHeap)
        {
-               
+               /* Free up the import arenas */
                if(psBMHeap->ui32Attribs
                &       (PVRSRV_BACKINGSTORE_SYSMEM_NONCONTIG
                        |PVRSRV_BACKINGSTORE_LOCALMEM_CONTIG))
@@ -1149,14 +1440,12 @@ BM_DestroyHeap (IMG_HANDLE hDevMemHeap)
                        return;
                }
 
-               
+               /* Free up the MMU Heap */
                psDeviceNode->pfnMMUDelete (psBMHeap->pMMUHeap);
 
-               
+               /* remove from the heap list */
                List_BM_HEAP_Remove(psBMHeap);
-               
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_HEAP), psBMHeap, IMG_NULL);
-               
        }
        else
        {
@@ -1165,6 +1454,17 @@ BM_DestroyHeap (IMG_HANDLE hDevMemHeap)
 }
 
 
+/*!
+******************************************************************************
+
+       @Function       BM_Reinitialise
+
+       @Description    Reinitialise the buffer manager after a power down event.
+
+       @Return         IMG_TRUE - Success
+                               IMG_FALSE - Failed
+
+ *****************************************************************************/
 IMG_BOOL
 BM_Reinitialise (PVRSRV_DEVICE_NODE *psDeviceNode)
 {
@@ -1172,16 +1472,48 @@ BM_Reinitialise (PVRSRV_DEVICE_NODE *psDeviceNode)
        PVR_DPF((PVR_DBG_MESSAGE, "BM_Reinitialise"));
        PVR_UNREFERENCED_PARAMETER(psDeviceNode);
 
+        /* FIXME: Need to reenable all contexts
+         List_BM_CONTEXT_ForEach(psDeviceNode->sDevMemoryInfo.pBMContext, MMU_Enable);
+        */
 
        return IMG_TRUE;
 }
 
+/*!
+******************************************************************************
+
+       @Function   BM_Alloc
+
+       @Description    Allocate a buffer mapped into both cpu and device virtual
+                               memory maps.
+
+       @Input      hDevMemHeap
+       @Input      psDevVAddr - device virtual address specified by caller (optional)
+       @Input      uSize - require size in bytes of the buffer.
+       @Input      pui32Flags - bit mask of buffer property flags.
+    @Input      uDevVAddrAlignment - required alignment in bytes, or 0.
+    @Input      pvPrivData - opaque private data passed through to allocator
+    @Input      ui32PrivDataLength - length of opaque private data
+
+       @Output     phBuf - receives buffer handle
+       @Output     pui32Flags - bit mask of heap property flags.
+
+       @Return         IMG_TRUE - Success
+                               IMG_FALSE - Failure
+
+ *****************************************************************************/
 IMG_BOOL
 BM_Alloc (  IMG_HANDLE                 hDevMemHeap,
                        IMG_DEV_VIRTADDR        *psDevVAddr,
                        IMG_SIZE_T                      uSize,
                        IMG_UINT32                      *pui32Flags,
                        IMG_UINT32                      uDevVAddrAlignment,
+                       IMG_PVOID                       pvPrivData,
+                       IMG_UINT32                      ui32PrivDataLength,
+                       IMG_UINT32                      ui32ChunkSize,
+                       IMG_UINT32                      ui32NumVirtChunks,
+                       IMG_UINT32                      ui32NumPhysChunks,
+                       IMG_BOOL                        *pabMapChunk,
                        BM_HANDLE                       *phBuf)
 {
        BM_BUF *pBuf;
@@ -1213,7 +1545,9 @@ BM_Alloc (  IMG_HANDLE                    hDevMemHeap,
                uDevVAddrAlignment = 1;
        }
 
-       
+       /*
+        * Allocate something in which to record the allocation's details.
+        */
        if (OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                   sizeof (BM_BUF),
                                   (IMG_PVOID *)&pBuf, IMG_NULL,
@@ -1224,17 +1558,25 @@ BM_Alloc (  IMG_HANDLE                  hDevMemHeap,
        }
        OSMemSet(pBuf, 0, sizeof (BM_BUF));
 
-       
+       /*
+        * Allocate the memory itself now.
+        */
        if (AllocMemory(pBMContext,
                                        psBMHeap,
                                        psDevVAddr,
                                        uSize,
                                        uFlags,
                                        uDevVAddrAlignment,
+                                       pvPrivData,
+                                       ui32PrivDataLength,
+                                       ui32ChunkSize,
+                                       ui32NumVirtChunks,
+                                       ui32NumPhysChunks,
+                                       pabMapChunk,
                                        pBuf) != IMG_TRUE)
        {
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof (BM_BUF), pBuf, IMG_NULL);
-               
+               /* not nulling pointer, out of scope */
                PVR_DPF((PVR_DBG_ERROR, "BM_Alloc: AllocMemory FAILED"));
                return IMG_FALSE;
        }
@@ -1243,12 +1585,17 @@ BM_Alloc (  IMG_HANDLE                  hDevMemHeap,
                  "BM_Alloc (uSize=0x%x, uFlags=0x%x)",
                  uSize, uFlags));
 
-       
+       /*
+        * Assign the handle and return.
+        */
        pBuf->ui32RefCount = 1;
        *phBuf = (BM_HANDLE)pBuf;
        *pui32Flags = uFlags | psBMHeap->ui32Attribs;
 
-       
+       /*
+        * If the user has specified heap CACHETYPE flags themselves,
+        * override any CACHETYPE flags inherited from the heap.
+        */
        if(uFlags & PVRSRV_HAP_CACHETYPE_MASK)
        {
                *pui32Flags &= ~PVRSRV_HAP_CACHETYPE_MASK;
@@ -1261,6 +1608,21 @@ BM_Alloc (  IMG_HANDLE                   hDevMemHeap,
 
 
 #if defined(PVR_LMA)
+/*!
+******************************************************************************
+
+       @Function   ValidSysPAddrArrayForDev
+
+       @Description    Verify the array of system address is accessible
+                    by the given device.
+
+       @Input      psDeviceNode
+    @Input      psSysPAddr - system address array
+    @Input      ui32PageSize - size of address array
+    
+       @Return     IMG_BOOL
+
+ *****************************************************************************/
 static IMG_BOOL
 ValidSysPAddrArrayForDev(PVRSRV_DEVICE_NODE *psDeviceNode, IMG_SYS_PHYADDR *psSysPAddr, IMG_UINT32 ui32PageCount, IMG_SIZE_T ui32PageSize)
 {
@@ -1287,6 +1649,21 @@ ValidSysPAddrArrayForDev(PVRSRV_DEVICE_NODE *psDeviceNode, IMG_SYS_PHYADDR *psSy
        return IMG_TRUE;
 }
 
+/*!
+******************************************************************************
+
+       @Function  ValidSysPAddrRangeForDev
+
+       @Description   Verify a system address range is accessible
+                  by the given device.
+
+       @Input      psDeviceNode
+    @Input      sStartSysPAddr - starting system address
+    @Input      ui32Range - length of address range
+
+       @Return     IMG_BOOL
+
+ *****************************************************************************/
 static IMG_BOOL
 ValidSysPAddrRangeForDev(PVRSRV_DEVICE_NODE *psDeviceNode, IMG_SYS_PHYADDR sStartSysPAddr, IMG_SIZE_T ui32Range)
 {
@@ -1314,6 +1691,28 @@ ValidSysPAddrRangeForDev(PVRSRV_DEVICE_NODE *psDeviceNode, IMG_SYS_PHYADDR sStar
 #endif
 
 
+/*!
+******************************************************************************
+
+       @Function   BM_Wrap
+
+       @Description    Create a buffer which wraps user provided system physical
+                               memory.
+                               The wrapped memory must be page aligned. BM_Wrap will
+                               roundup the size to a multiple of cpu pages.
+
+       @Input      ui32Size - size of memory to wrap.
+       @Input      ui32Offset - Offset into page of memory to wrap.
+       @Input      bPhysContig - Is the wrap physically contiguous.
+       @Input      psSysAddr - list of system physical page addresses of memory to wrap.
+       @Input      pvCPUVAddr - optional CPU kernel virtual address (Page aligned) of memory to wrap.
+    @Input      uFlags - bit mask of buffer property flags.
+    @output     phBuf - receives the buffer handle.
+
+       @Return         IMG_TRUE - Success.
+                               IMG_FALSE - Failed
+
+ *****************************************************************************/
 IMG_BOOL
 BM_Wrap (      IMG_HANDLE hDevMemHeap,
                        IMG_SIZE_T ui32Size,
@@ -1368,20 +1767,23 @@ BM_Wrap (       IMG_HANDLE hDevMemHeap,
                }
        }
 #endif
-       
+       /*
+        * Insert the System Physical Address of the first page into the hash so we can optimise multiple wraps of the
+        * same memory.
+        */
        sHashAddress = psSysAddr[0];
 
-       
+       /* Add the in-page offset to ensure a unique hash */
        sHashAddress.uiAddr += ui32Offset;
 
-       
+       /* See if this address has already been wrapped */
        pBuf = (BM_BUF *)HASH_Retrieve(psBMContext->pBufferHash, sHashAddress.uiAddr);
 
        if(pBuf)
        {
                IMG_SIZE_T ui32MappingSize = HOST_PAGEALIGN (ui32Size + ui32Offset);
 
-               
+               /* Check base address, size and contiguity type match */
                if(pBuf->pMapping->uSize == ui32MappingSize && (pBuf->pMapping->eCpuMemoryOrigin == hm_wrapped ||
                                                                                                                pBuf->pMapping->eCpuMemoryOrigin == hm_wrapped_virtaddr))
                {
@@ -1389,7 +1791,7 @@ BM_Wrap ( IMG_HANDLE hDevMemHeap,
                                        "BM_Wrap (Matched previous Wrap! uSize=0x%x, uOffset=0x%x, SysAddr=%08X)",
                                        ui32Size, ui32Offset, sHashAddress.uiAddr));
 
-                       pBuf->ui32RefCount++;
+                       PVRSRVBMBufIncRef(pBuf);
                        *phBuf = (BM_HANDLE)pBuf;
                        if(pui32Flags)
                                *pui32Flags = uFlags;
@@ -1398,12 +1800,15 @@ BM_Wrap (       IMG_HANDLE hDevMemHeap,
                }
                else
                {
-                 
+                 /* Otherwise removed that item from the hash table 
+                        (a workaround for buffer device class) */
                        HASH_Remove(psBMContext->pBufferHash, (IMG_UINTPTR_T)sHashAddress.uiAddr);
                }       
        }
 
-       
+       /*
+        * Allocate something in which to record the allocation's details.
+        */
        if (OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                                sizeof (BM_BUF),
                                                (IMG_PVOID *)&pBuf, IMG_NULL,
@@ -1414,19 +1819,23 @@ BM_Wrap (       IMG_HANDLE hDevMemHeap,
        }
        OSMemSet(pBuf, 0, sizeof (BM_BUF));
 
-       
+       /*
+        * Actually perform the memory wrap.
+        */
        if (WrapMemory (psBMHeap, ui32Size, ui32Offset, bPhysContig, psSysAddr, pvCPUVAddr, uFlags, pBuf) != IMG_TRUE)
        {
                PVR_DPF((PVR_DBG_ERROR, "BM_Wrap: WrapMemory FAILED"));
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof (BM_BUF), pBuf, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
                return IMG_FALSE;
        }
 
-       
+       /* Only insert the buffer in the hash table if it is contiguous - allows for optimisation of multiple wraps
+        * of the same contiguous buffer.
+        */
        if(pBuf->pMapping->eCpuMemoryOrigin == hm_wrapped || pBuf->pMapping->eCpuMemoryOrigin == hm_wrapped_virtaddr)
        {
-               
+               /* Have we calculated the right Hash key ? */
                PVR_ASSERT(SysSysPAddrToCpuPAddr(sHashAddress).uiAddr == pBuf->CpuPAddr.uiAddr);
 
                if (!HASH_Insert (psBMContext->pBufferHash, sHashAddress.uiAddr, (IMG_UINTPTR_T)pBuf))
@@ -1441,36 +1850,73 @@ BM_Wrap (       IMG_HANDLE hDevMemHeap,
                        "BM_Wrap (uSize=0x%x, uFlags=0x%x, devVAddr=%08X)",
                        ui32Size, uFlags, pBuf->DevVAddr.uiAddr));
 
-       
+       /*
+        * Assign the handle and return.
+        */
        pBuf->ui32RefCount = 1;
        *phBuf = (BM_HANDLE)pBuf;
        if(pui32Flags)
        {
-               
+               /* need to override the heap attributes SINGLE PROC to MULT_PROC. */
                *pui32Flags = (uFlags & ~PVRSRV_HAP_MAPTYPE_MASK) | PVRSRV_HAP_MULTI_PROCESS;
        }
 
        return IMG_TRUE;
 }
 
+/*!
+******************************************************************************
+
+       @Function   BM_Export
+
+       @Description    Export a buffer previously allocated via BM_Alloc.
+
+       @Input      hBuf - buffer handle.
+       @Input      ui32Flags - flags
+
+       @Return         None.
+
+ *****************************************************************************/
+
 IMG_VOID
 BM_Export (BM_HANDLE hBuf)
 {
        BM_BUF *pBuf = (BM_BUF *)hBuf;
 
-       pBuf->ui32ExportCount++;
+       PVRSRVBMBufIncExport(pBuf);
 }
 
+/*!
+******************************************************************************
+ @Function             BM_Export
+
+ @Description  Export a buffer previously allocated via BM_Alloc.
+
+ @Input         hBuf - buffer handle.
+
+ @Return               None.
+**************************************************************************/
 IMG_VOID
 BM_FreeExport(BM_HANDLE hBuf,
                IMG_UINT32 ui32Flags)
 {
        BM_BUF *pBuf = (BM_BUF *)hBuf;
 
-       pBuf->ui32ExportCount--;
+       PVRSRVBMBufDecExport(pBuf);
        FreeBuf (pBuf, ui32Flags, IMG_FALSE);
 }
 
+/*!
+******************************************************************************
+ @Function             BM_FreeExport
+
+ @Description  Free a buffer previously exported via BM_Export.
+
+ @Input         hBuf - buffer handle.
+ @Input         ui32Flags - flags
+
+ @Return               None.
+**************************************************************************/
 IMG_VOID
 BM_Free (BM_HANDLE hBuf,
                IMG_UINT32 ui32Flags)
@@ -1490,8 +1936,7 @@ BM_Free (BM_HANDLE hBuf,
 
        SysAcquireData(&psSysData);
 
-       pBuf->ui32RefCount--;
-
+       PVRSRVBMBufDecRef(pBuf);
        if(pBuf->ui32RefCount == 0)
        {
                if(pBuf->pMapping->eCpuMemoryOrigin == hm_wrapped || pBuf->pMapping->eCpuMemoryOrigin == hm_wrapped_virtaddr)
@@ -1505,6 +1950,18 @@ BM_Free (BM_HANDLE hBuf,
 }
 
 
+/*!
+******************************************************************************
+
+       @Function   BM_HandleToCpuVaddr
+
+       @Description    Retreive the cpu virtual address associated with a buffer.
+
+       @Input      buffer handle.
+
+       @Return         buffers cpu virtual address, or NULL if none exists
+
+ *****************************************************************************/
 IMG_CPU_VIRTADDR
 BM_HandleToCpuVaddr (BM_HANDLE hBuf)
 {
@@ -1524,6 +1981,18 @@ BM_HandleToCpuVaddr (BM_HANDLE hBuf)
 }
 
 
+/*!
+******************************************************************************
+
+       @Function   BM_HandleToDevVaddr
+
+       @Description    Retreive the device virtual address associated with a buffer.
+
+       @Input      hBuf - buffer handle.
+
+       @Return         buffers device virtual address.
+
+ *****************************************************************************/
 IMG_DEV_VIRTADDR
 BM_HandleToDevVaddr (BM_HANDLE hBuf)
 {
@@ -1542,6 +2011,18 @@ BM_HandleToDevVaddr (BM_HANDLE hBuf)
 }
 
 
+/*!
+******************************************************************************
+
+       @Function   BM_HandleToSysPaddr
+
+       @Description    Retreive the system physical address associated with a buffer.
+
+       @Input      hBuf - buffer handle.
+
+       @Return         buffers device virtual address.
+
+ *****************************************************************************/
 IMG_SYS_PHYADDR
 BM_HandleToSysPaddr (BM_HANDLE hBuf)
 {
@@ -1560,6 +2041,18 @@ BM_HandleToSysPaddr (BM_HANDLE hBuf)
        return SysCpuPAddrToSysPAddr (pBuf->CpuPAddr);
 }
 
+/*!
+******************************************************************************
+
+       @Function   BM_HandleToMemOSHandle
+
+       @Description    Retreive the underlying memory handle associated with a buffer.
+
+       @Input      hBuf - buffer handle.
+
+       @Return         OS Specific memory handle.
+
+ *****************************************************************************/
 IMG_HANDLE
 BM_HandleToOSMemHandle(BM_HANDLE hBuf)
 {
@@ -1579,6 +2072,33 @@ BM_HandleToOSMemHandle(BM_HANDLE hBuf)
        return pBuf->hOSMemHandle;
 }
 
+/*!
+******************************************************************************
+
+       @Function   DevMemoryAlloc
+
+       @Description    Allocate device memory for a given physical/virtual memory
+                               mapping.  We handle the main cases where device MMU mappings
+                               are required - these are the dynamic cases: all wrappings of
+                               host OS memory and host OS imports for SYS_MMU_NORMAL mode.
+
+                               If no MMU support is required then we simply map device virtual
+                               space as device physical space.
+
+       @Input      pBMContext  - the pager to allocate from.
+       @Output     pMapping - the mapping descriptor to be filled in for this
+                                        allocation.
+       @Output     pActualSize - the actual size of the block allocated in
+                                        bytes.
+       @Input      uFlags -  allocation flags
+       @Input      dev_vaddr_alignment - required device virtual address
+                                        alignment, or 0.
+       @Output     pDevVAddr - receives the device virtual base address of the
+                                        allocated block.
+       @Return         IMG_TRUE - Success
+                               IMG_FALSE - Failed.
+
+ *****************************************************************************/
 static IMG_BOOL
 DevMemoryAlloc (BM_CONTEXT *pBMContext,
                                BM_MAPPING *pMapping,
@@ -1596,21 +2116,23 @@ DevMemoryAlloc (BM_CONTEXT *pBMContext,
 
        if(uFlags & PVRSRV_MEM_INTERLEAVED)
        {
-               
+               /* double the size */
                pMapping->uSize *= 2;
        }
 
 #ifdef PDUMP
        if(uFlags & PVRSRV_MEM_DUMMY)
        {
-               
+               /* only one page behind a dummy allocation */
                ui32PDumpSize = pMapping->pBMHeap->sDevArena.ui32DataPageSize;
        }
 #endif
 
-       
+       /* Check we haven't fall through a gap */
+       PVR_ASSERT(pMapping->uSizeVM != 0);
+       /* allocate device linear space */
        if (!psDeviceNode->pfnMMUAlloc (pMapping->pBMHeap->pMMUHeap,
-                                                                       pMapping->uSize,
+                                                                       pMapping->uSizeVM,
                                                                        pActualSize,
                                                                        0,
                                                                        dev_vaddr_alignment,
@@ -1625,7 +2147,7 @@ DevMemoryAlloc (BM_CONTEXT *pBMContext,
 #endif
 
 #if defined(PDUMP)
-       
+       /* pdump the memory allocate */
        PDUMPMALLOCPAGES(&psDeviceNode->sDevId,
                                         pMapping->DevVAddr.uiAddr,
                                         pMapping->CpuVAddr,
@@ -1635,8 +2157,8 @@ DevMemoryAlloc (BM_CONTEXT *pBMContext,
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
                                         psDeviceNode->pfnMMUIsHeapShared(pMapping->pBMHeap->pMMUHeap),
 #else
-                                        IMG_FALSE, 
-#endif 
+                                        IMG_FALSE, // unused
+#endif /* SUPPORT_PDUMP_MULTI_PROCESS */
                                         (IMG_HANDLE)pMapping);
 #endif
 
@@ -1646,26 +2168,61 @@ DevMemoryAlloc (BM_CONTEXT *pBMContext,
                case hm_wrapped_virtaddr:
                case hm_contiguous:
                {
-                       psDeviceNode->pfnMMUMapPages (  pMapping->pBMHeap->pMMUHeap,
-                                                       pMapping->DevVAddr,
-                                                       SysCpuPAddrToSysPAddr (pMapping->CpuPAddr),
-                                                       pMapping->uSize,
-                                                       uFlags,
-                                                       (IMG_HANDLE)pMapping);
-
+                       if (uFlags & PVRSRV_MEM_SPARSE)
+                       {
+                               /* Check if this device supports sparse mappings */
+                               PVR_ASSERT(psDeviceNode->pfnMMUMapPagesSparse != IMG_NULL);
+                               psDeviceNode->pfnMMUMapPagesSparse(pMapping->pBMHeap->pMMUHeap,
+                                                               pMapping->DevVAddr,
+                                                               SysCpuPAddrToSysPAddr (pMapping->CpuPAddr),
+                                                               pMapping->ui32ChunkSize,
+                                                               pMapping->ui32NumVirtChunks,
+                                                               pMapping->ui32NumPhysChunks,
+                                                               pMapping->pabMapChunk,
+                                                               uFlags,
+                                                               (IMG_HANDLE)pMapping);
+                       }
+                       else
+                       {
+                               psDeviceNode->pfnMMUMapPages (  pMapping->pBMHeap->pMMUHeap,
+                                                               pMapping->DevVAddr,
+                                                               SysCpuPAddrToSysPAddr (pMapping->CpuPAddr),
+                                                               pMapping->uSize,
+                                                               uFlags,
+                                                               (IMG_HANDLE)pMapping);
+                       }
                        *pDevVAddr = pMapping->DevVAddr;
                        break;
                }
                case hm_env:
                {
-                       psDeviceNode->pfnMMUMapShadow ( pMapping->pBMHeap->pMMUHeap,
-                                                       pMapping->DevVAddr,
-                                                       pMapping->uSize,
-                                                       pMapping->CpuVAddr,
-                                                       pMapping->hOSMemHandle,
-                                                       pDevVAddr,
-                                                       uFlags,
-                                                       (IMG_HANDLE)pMapping);
+                       if (uFlags & PVRSRV_MEM_SPARSE)
+                       {
+                               /* Check if this device supports sparse mappings */
+                               PVR_ASSERT(psDeviceNode->pfnMMUMapShadowSparse != IMG_NULL);
+                               psDeviceNode->pfnMMUMapShadowSparse(pMapping->pBMHeap->pMMUHeap,
+                                                               pMapping->DevVAddr,
+                                                               pMapping->ui32ChunkSize,
+                                                               pMapping->ui32NumVirtChunks,
+                                                               pMapping->ui32NumPhysChunks,
+                                                               pMapping->pabMapChunk,
+                                                               pMapping->CpuVAddr,
+                                                               pMapping->hOSMemHandle,
+                                                               pDevVAddr,
+                                                               uFlags,
+                                                               (IMG_HANDLE)pMapping);
+                       }
+                       else
+                       {
+                               psDeviceNode->pfnMMUMapShadow ( pMapping->pBMHeap->pMMUHeap,
+                                                               pMapping->DevVAddr,
+                                                               pMapping->uSize,
+                                                               pMapping->CpuVAddr,
+                                                               pMapping->hOSMemHandle,
+                                                               pDevVAddr,
+                                                               uFlags,
+                                                               (IMG_HANDLE)pMapping);
+                       }
                        break;
                }
                case hm_wrapped_scatter:
@@ -1710,10 +2267,10 @@ DevMemoryFree (BM_MAPPING *pMapping)
        if (sDevPAddr.uiAddr != 0)
        {
 #ifdef PDUMP
-               
+               /* pdump the memory free */
                if(pMapping->ui32Flags & PVRSRV_MEM_DUMMY)
                {
-                       
+                       /* physical memory size differs in the case of Dummy allocations */
                        ui32PSize = pMapping->pBMHeap->sDevArena.ui32DataPageSize;
                }
                else
@@ -1726,37 +2283,37 @@ DevMemoryFree (BM_MAPPING *pMapping)
                            ui32PSize,
                            pMapping->pBMHeap->sDevArena.ui32DataPageSize,
                            (IMG_HANDLE)pMapping,
-                           (pMapping->ui32Flags & PVRSRV_MEM_INTERLEAVED) ? IMG_TRUE : IMG_FALSE);
+                           (pMapping->ui32Flags & PVRSRV_MEM_INTERLEAVED) ? IMG_TRUE : IMG_FALSE,
+                           (pMapping->ui32Flags & PVRSRV_MEM_SPARSE) ? IMG_TRUE : IMG_FALSE);
 #endif
        }
-       psDeviceNode->pfnMMUFree (pMapping->pBMHeap->pMMUHeap, pMapping->DevVAddr, IMG_CAST_TO_DEVVADDR_UINT(pMapping->uSize));
+       PVR_ASSERT(pMapping->uSizeVM != 0);
+       psDeviceNode->pfnMMUFree (pMapping->pBMHeap->pMMUHeap, pMapping->DevVAddr, IMG_CAST_TO_DEVVADDR_UINT(pMapping->uSizeVM));
 }
 
+/* If this array grows larger, it might be preferable to use a hashtable rather than an array. */
 #ifndef XPROC_WORKAROUND_NUM_SHAREABLES
 #define XPROC_WORKAROUND_NUM_SHAREABLES 200
 #endif
 
 #define XPROC_WORKAROUND_BAD_SHAREINDEX 0773407734
 
+#define XPROC_WORKAROUND_UNKNOWN       0
+#define XPROC_WORKAROUND_ALLOC         1
+#define XPROC_WORKAROUND_MAP           2
+
 static IMG_UINT32 gXProcWorkaroundShareIndex = XPROC_WORKAROUND_BAD_SHAREINDEX;
+static IMG_UINT32 gXProcWorkaroundState = XPROC_WORKAROUND_UNKNOWN;
 
-static struct {
-       IMG_UINT32 ui32RefCount;
-       IMG_UINT32 ui32AllocFlags;
-       IMG_UINT32 ui32Size;
-       IMG_UINT32 ui32PageSize;
-    RA_ARENA *psArena;
-    IMG_SYS_PHYADDR sSysPAddr;
-       IMG_VOID *pvCpuVAddr;
-       IMG_HANDLE hOSMemHandle;
-} gXProcWorkaroundShareData[XPROC_WORKAROUND_NUM_SHAREABLES] = {{0}};
+/* PRQA S 0686 10 */ /* force compiler to init structure */
+XPROC_DATA gXProcWorkaroundShareData[XPROC_WORKAROUND_NUM_SHAREABLES] = {{0}};
 
 PVRSRV_ERROR BM_XProcWorkaroundSetShareIndex(IMG_UINT32 ui32Index)
 {
-       
-
-
+       /* if you fail this assertion - did you acquire the mutex?
+          did you call "set" exactly once?
+          did you call "unset" exactly once per set?
+       */
        if (gXProcWorkaroundShareIndex != XPROC_WORKAROUND_BAD_SHAREINDEX)
        {
                PVR_DPF((PVR_DBG_ERROR, "No, it's already set!"));
@@ -1764,15 +2321,17 @@ PVRSRV_ERROR BM_XProcWorkaroundSetShareIndex(IMG_UINT32 ui32Index)
        }
 
        gXProcWorkaroundShareIndex = ui32Index;
+       gXProcWorkaroundState = XPROC_WORKAROUND_MAP;
 
        return PVRSRV_OK;
 }
 
 PVRSRV_ERROR BM_XProcWorkaroundUnsetShareIndex(IMG_UINT32 ui32Index)
 {
-       
-
-
+       /* if you fail this assertion - did you acquire the mutex?
+          did you call "set" exactly once?
+          did you call "unset" exactly once per set?
+       */
        if (gXProcWorkaroundShareIndex == XPROC_WORKAROUND_BAD_SHAREINDEX)
        {
                PVR_DPF((PVR_DBG_ERROR, "huh?   how can it be bad??"));
@@ -1785,15 +2344,17 @@ PVRSRV_ERROR BM_XProcWorkaroundUnsetShareIndex(IMG_UINT32 ui32Index)
        }
 
        gXProcWorkaroundShareIndex = XPROC_WORKAROUND_BAD_SHAREINDEX;
+       gXProcWorkaroundState = XPROC_WORKAROUND_UNKNOWN;
 
        return PVRSRV_OK;
 }
 
 PVRSRV_ERROR BM_XProcWorkaroundFindNewBufferAndSetShareIndex(IMG_UINT32 *pui32Index)
 {
-       
-
-
+       /* if you fail this assertion - did you acquire the mutex?
+          did you call "set" exactly once?
+          did you call "unset" exactly once per set?
+       */
        if (gXProcWorkaroundShareIndex != XPROC_WORKAROUND_BAD_SHAREINDEX)
        {
                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -1804,6 +2365,7 @@ PVRSRV_ERROR BM_XProcWorkaroundFindNewBufferAndSetShareIndex(IMG_UINT32 *pui32In
                if (gXProcWorkaroundShareData[*pui32Index].ui32RefCount == 0)
                {
                        gXProcWorkaroundShareIndex = *pui32Index;
+                       gXProcWorkaroundState = XPROC_WORKAROUND_ALLOC;
                        return PVRSRV_OK;
                }
        }
@@ -1812,16 +2374,13 @@ PVRSRV_ERROR BM_XProcWorkaroundFindNewBufferAndSetShareIndex(IMG_UINT32 *pui32In
        return PVRSRV_ERROR_OUT_OF_MEMORY;
 }
 
-IMG_UINT32 BM_XProcWorkaroundGetRefCount(IMG_UINT32 ui32Index)
-{
-       return gXProcWorkaroundShareData[ui32Index].ui32RefCount;
-}
-
 static PVRSRV_ERROR
 XProcWorkaroundAllocShareable(RA_ARENA *psArena,
                               IMG_UINT32 ui32AllocFlags,
                               IMG_UINT32 ui32Size,
                               IMG_UINT32 ui32PageSize,
+                                                         IMG_PVOID pvPrivData,
+                                                         IMG_UINT32 ui32PrivDataLength,
                               IMG_VOID **ppvCpuVAddr,
                               IMG_HANDLE *phOSMemHandle)
 {
@@ -1865,12 +2424,20 @@ XProcWorkaroundAllocShareable(RA_ARENA *psArena,
                *ppvCpuVAddr = gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].pvCpuVAddr;
                *phOSMemHandle = gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].hOSMemHandle;
 
-               gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].ui32RefCount ++;
+               BM_XProcIndexAcquire(gXProcWorkaroundShareIndex);
 
                return PVRSRV_OK;
        }
        else
        {
+               if (gXProcWorkaroundState != XPROC_WORKAROUND_ALLOC)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,
+                                        "XPROC workaround in bad state! About to allocate memory from non-alloc state! (%d)",
+                                        gXProcWorkaroundState));
+               }
+               PVR_ASSERT(gXProcWorkaroundState == XPROC_WORKAROUND_ALLOC);
+
                if (psArena != IMG_NULL)
                {
                        IMG_CPU_PHYADDR sCpuPAddr;
@@ -1886,6 +2453,8 @@ XProcWorkaroundAllocShareable(RA_ARENA *psArena,
                                                   0,
                            ui32PageSize,
                                                   0,
+                                                  pvPrivData,
+                                                  ui32PrivDataLength,
                                                   (IMG_UINTPTR_T *)&sSysPAddr.uiAddr))
                        {
                                PVR_DPF((PVR_DBG_ERROR, "XProcWorkaroundAllocShareable: RA_Alloc(0x%x) FAILED", ui32Size));
@@ -1896,6 +2465,7 @@ XProcWorkaroundAllocShareable(RA_ARENA *psArena,
                        if(OSReservePhys(sCpuPAddr,
                                                         ui32Size,
                                                         ui32AllocFlags,
+                                                        IMG_NULL,
                                                         (IMG_VOID **)&gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].pvCpuVAddr,
                              &gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].hOSMemHandle) != PVRSRV_OK)
             {
@@ -1912,10 +2482,13 @@ XProcWorkaroundAllocShareable(RA_ARENA *psArena,
             ui32AllocFlags &= ~PVRSRV_HAP_MAPTYPE_MASK;
             ui32AllocFlags |= PVRSRV_HAP_SINGLE_PROCESS;
 
-            
+            /* allocate pages from the OS RAM */
             if (OSAllocPages(ui32AllocFlags,
                              ui32Size,
                              ui32PageSize,
+                                                        pvPrivData,
+                                                        ui32PrivDataLength,
+                                                        IMG_NULL,      /* FIXME: to support cross process sparse allocations */
                              (IMG_VOID **)&gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].pvCpuVAddr,
                              &gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].hOSMemHandle) != PVRSRV_OK)
             {
@@ -1934,7 +2507,7 @@ XProcWorkaroundAllocShareable(RA_ARENA *psArena,
                *ppvCpuVAddr = gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].pvCpuVAddr;
                *phOSMemHandle = gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].hOSMemHandle;
 
-               gXProcWorkaroundShareData[gXProcWorkaroundShareIndex].ui32RefCount ++;
+               BM_XProcIndexAcquire(gXProcWorkaroundShareIndex);
 
                return PVRSRV_OK;
        }
@@ -1942,7 +2515,6 @@ XProcWorkaroundAllocShareable(RA_ARENA *psArena,
 
 static PVRSRV_ERROR XProcWorkaroundHandleToSI(IMG_HANDLE hOSMemHandle, IMG_UINT32 *pui32SI)
 {
-       
        IMG_UINT32 ui32SI;
        IMG_BOOL bFound;
        IMG_BOOL bErrorDups;
@@ -1974,59 +2546,113 @@ static PVRSRV_ERROR XProcWorkaroundHandleToSI(IMG_HANDLE hOSMemHandle, IMG_UINT3
        return PVRSRV_OK;
 }
 
-static IMG_VOID XProcWorkaroundFreeShareable(IMG_HANDLE hOSMemHandle)
+#if defined(PVRSRV_REFCOUNT_DEBUG)
+IMG_VOID _BM_XProcIndexAcquireDebug(const IMG_CHAR *pszFile, IMG_INT iLine, IMG_UINT32 ui32Index)
+#else
+IMG_VOID _BM_XProcIndexAcquire(IMG_UINT32 ui32Index)
+#endif
 {
-       IMG_UINT32 ui32SI = (IMG_UINT32)((IMG_UINTPTR_T)hOSMemHandle & 0xffffU);
-       PVRSRV_ERROR eError;
-
-       eError = XProcWorkaroundHandleToSI(hOSMemHandle, &ui32SI);
-       if (eError != PVRSRV_OK)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "bad handle"));
-               return;
-       }
+#if defined(PVRSRV_REFCOUNT_DEBUG)
+       PVRSRVBMXProcIncRef2(pszFile, iLine, ui32Index);
+#else
+       PVRSRVBMXProcIncRef(ui32Index);
+#endif
+}
 
-       gXProcWorkaroundShareData[ui32SI].ui32RefCount --;
+#if defined(PVRSRV_REFCOUNT_DEBUG)
+IMG_VOID _BM_XProcIndexReleaseDebug(const IMG_CHAR *pszFile, IMG_INT iLine, IMG_UINT32 ui32Index)
+#else
+IMG_VOID _BM_XProcIndexRelease(IMG_UINT32 ui32Index)
+#endif
+{
+#if defined(PVRSRV_REFCOUNT_DEBUG)
+       PVRSRVBMXProcDecRef2(pszFile, iLine, ui32Index);
+#else
+       PVRSRVBMXProcDecRef(ui32Index);
+#endif
 
        PVR_DPF((PVR_DBG_VERBOSE, "Reduced refcount of SI[%d] from %d to %d",
-                        ui32SI, gXProcWorkaroundShareData[ui32SI].ui32RefCount+1, gXProcWorkaroundShareData[ui32SI].ui32RefCount));
+                        ui32Index, gXProcWorkaroundShareData[ui32Index].ui32RefCount+1, gXProcWorkaroundShareData[ui32Index].ui32RefCount));
 
-       if (gXProcWorkaroundShareData[ui32SI].ui32RefCount == 0)
+       if (gXProcWorkaroundShareData[ui32Index].ui32RefCount == 0)
        {
-               if (gXProcWorkaroundShareData[ui32SI].psArena != IMG_NULL)
+               if (gXProcWorkaroundShareData[ui32Index].psArena != IMG_NULL)
                {
                        IMG_SYS_PHYADDR sSysPAddr;
 
-                       if (gXProcWorkaroundShareData[ui32SI].pvCpuVAddr != IMG_NULL)
+                       if (gXProcWorkaroundShareData[ui32Index].pvCpuVAddr != IMG_NULL)
                        {
-                               OSUnReservePhys(gXProcWorkaroundShareData[ui32SI].pvCpuVAddr,
-                                                               gXProcWorkaroundShareData[ui32SI].ui32Size,
-                                                               gXProcWorkaroundShareData[ui32SI].ui32AllocFlags,
-                                                               gXProcWorkaroundShareData[ui32SI].hOSMemHandle);
+                               OSUnReservePhys(gXProcWorkaroundShareData[ui32Index].pvCpuVAddr,
+                                                               gXProcWorkaroundShareData[ui32Index].ui32Size,
+                                                               gXProcWorkaroundShareData[ui32Index].ui32AllocFlags,
+                                                               gXProcWorkaroundShareData[ui32Index].hOSMemHandle);
                        }
-                       sSysPAddr = gXProcWorkaroundShareData[ui32SI].sSysPAddr;
-                       RA_Free (gXProcWorkaroundShareData[ui32SI].psArena,
+                       sSysPAddr = gXProcWorkaroundShareData[ui32Index].sSysPAddr;
+                       RA_Free (gXProcWorkaroundShareData[ui32Index].psArena,
                                         sSysPAddr.uiAddr,
                                         IMG_FALSE);
                }
                else
                {
                        PVR_DPF((PVR_DBG_VERBOSE, "freeing OS memory"));
-                       OSFreePages(gXProcWorkaroundShareData[ui32SI].ui32AllocFlags,
-                                               gXProcWorkaroundShareData[ui32SI].ui32PageSize,
-                                               gXProcWorkaroundShareData[ui32SI].pvCpuVAddr,
-                                               gXProcWorkaroundShareData[ui32SI].hOSMemHandle);
+                       OSFreePages(gXProcWorkaroundShareData[ui32Index].ui32AllocFlags,
+                                               gXProcWorkaroundShareData[ui32Index].ui32PageSize,
+                                               gXProcWorkaroundShareData[ui32Index].pvCpuVAddr,
+                                               gXProcWorkaroundShareData[ui32Index].hOSMemHandle);
                }
        }
 }
 
+static IMG_VOID XProcWorkaroundFreeShareable(IMG_HANDLE hOSMemHandle)
+{
+       IMG_UINT32 ui32SI = (IMG_UINT32)((IMG_UINTPTR_T)hOSMemHandle & 0xffffU);
+       PVRSRV_ERROR eError;
 
+       eError = XProcWorkaroundHandleToSI(hOSMemHandle, &ui32SI);
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "bad handle"));
+               return;
+       }
+
+       BM_XProcIndexRelease(ui32SI);
+}
+
+
+/*!
+******************************************************************************
+
+       @Function   BM_ImportMemory
+
+       @Description    Provide a resource allocator with a source of pages of memory
+                               from the Host OS's own allocation.  Allocates a block of pages
+                               larger than requested, allowing the resource allocator to
+                               operate a small cache of pre allocated pages.
+
+       @Input      pH - buffer manager handle, not the void type is dictated
+                                        by the generic nature of the resource allocator interface.
+       @Input      uRequestSize - requested size in bytes
+       @Output     pActualSize - receives the actual size allocated in bytes
+                                        which may be >= requested size
+       @Output     ppsMapping - receives the arbitrary user reference
+                                        associated with the underlying storage.
+       @Input      uFlags - bit mask of allocation flags
+    @Input      pvPrivData - opaque private data passed through to allocator
+    @Input      ui32PrivDataLength - length of opaque private data
+       @Output     pBase - receives a pointer to the allocated storage.
+
+       @Return         IMG_TRUE - success
+                               IMG_FALSE - failed
+
+ *****************************************************************************/
 static IMG_BOOL
 BM_ImportMemory (IMG_VOID *pH,
                          IMG_SIZE_T uRequestSize,
                          IMG_SIZE_T *pActualSize,
                          BM_MAPPING **ppsMapping,
                          IMG_UINT32 uFlags,
+                         IMG_PVOID pvPrivData,
+                         IMG_UINT32 ui32PrivDataLength,
                          IMG_UINTPTR_T *pBase)
 {
        BM_MAPPING *pMapping;
@@ -2035,7 +2661,7 @@ BM_ImportMemory (IMG_VOID *pH,
        IMG_BOOL bResult;
        IMG_SIZE_T uSize;
        IMG_SIZE_T uPSize;
-       IMG_SIZE_T uDevVAddrAlignment = 0; 
+       IMG_SIZE_T uDevVAddrAlignment = 0; /* ? */
 
        PVR_DPF ((PVR_DBG_MESSAGE,
                          "BM_ImportMemory (pBMContext=0x%x, uRequestSize=0x%x, uFlags=0x%x, uAlign=0x%x)",
@@ -2067,16 +2693,24 @@ BM_ImportMemory (IMG_VOID *pH,
        pMapping->DevVAddr.uiAddr = 0;
        pMapping->CpuPAddr.uiAddr = 0;
        pMapping->uSize = uSize;
+       if ((uFlags & PVRSRV_MEM_SPARSE) == 0)
+       {
+               pMapping->uSizeVM = uSize;
+       }
        pMapping->pBMHeap = pBMHeap;
        pMapping->ui32Flags = uFlags;
 
-       
+       /*
+        * If anyone want's to know, pass back the actual size of our allocation.
+        * There could be up to an extra page's worth of memory which will be marked
+        * as free in the RA.
+        */
        if (pActualSize)
        {
                *pActualSize = uSize;
        }
 
-       
+       /* if it's a dummy allocation only use one physical page */
        if(pMapping->ui32Flags & PVRSRV_MEM_DUMMY)
        {
                uPSize = pBMHeap->sDevArena.ui32DataPageSize;
@@ -2091,13 +2725,15 @@ BM_ImportMemory (IMG_VOID *pH,
                IMG_UINT32 ui32Attribs = pBMHeap->ui32Attribs | PVRSRV_MEM_XPROC;
         IMG_BOOL bBadBackingStoreType;
 
-        bBadBackingStoreType = IMG_TRUE; 
+        if(uFlags & PVRSRV_MEM_ION)
+        {
+            ui32Attribs |= PVRSRV_MEM_ION;
+        }
+
+        bBadBackingStoreType = IMG_TRUE;
 
-               if ((ui32Attribs & PVRSRV_BACKINGSTORE_SYSMEM_NONCONTIG) != 0)
+        if ((ui32Attribs & PVRSRV_BACKINGSTORE_SYSMEM_NONCONTIG) != 0)
         {
-#ifndef MAX
-#define MAX(a,b) ((a) > (b) ? (a) : (b))
-#endif
                uDevVAddrAlignment = MAX(pBMHeap->sDevArena.ui32DataPageSize, HOST_PAGESIZE());
 
 
@@ -2106,20 +2742,24 @@ BM_ImportMemory (IMG_VOID *pH,
                        PVR_DPF((PVR_DBG_ERROR, "Cannot use use this memory sharing workaround with allocations that might be suballocated"));
                        goto fail_mapping_alloc;
                }
-               uDevVAddrAlignment = 0; 
+               uDevVAddrAlignment = 0; /* FIXME: find out why it doesn't work if alignment is specified */
 
-               
+               /* If the user has specified heap CACHETYPE flags, use them to
+                * override the flags inherited from the heap.
+                */
                if (pMapping->ui32Flags & PVRSRV_HAP_CACHETYPE_MASK)
                {
                        ui32Attribs &= ~PVRSRV_HAP_CACHETYPE_MASK;
                        ui32Attribs |= (pMapping->ui32Flags & PVRSRV_HAP_CACHETYPE_MASK);
                }
 
-               
+               /* allocate "shared" pages. */
                if (XProcWorkaroundAllocShareable(IMG_NULL,
                                           ui32Attribs,
-                                                          (IMG_UINT32)uPSize,
+                                                                                 (IMG_UINT32)uPSize,
                                           pBMHeap->sDevArena.ui32DataPageSize,
+                                                                                 pvPrivData,
+                                                                                 ui32PrivDataLength,
                                           (IMG_VOID **)&pMapping->CpuVAddr,
                                           &pMapping->hOSMemHandle) != PVRSRV_OK)
                {
@@ -2129,36 +2769,41 @@ BM_ImportMemory (IMG_VOID *pH,
                        goto fail_mapping_alloc;
                }
 
-               
-               
-
+               /* specify how page addresses are derived */
+               /* it works just like "env" now - no need to record
+                  it as shareable, as we use the actual hOSMemHandle
+                  and only divert to our wrapper layer based on Attribs */
                pMapping->eCpuMemoryOrigin = hm_env;
-        bBadBackingStoreType = IMG_FALSE;
+               bBadBackingStoreType = IMG_FALSE;
         }
 
-               if ((ui32Attribs & PVRSRV_BACKINGSTORE_LOCALMEM_CONTIG) != 0)
+        if ((ui32Attribs & PVRSRV_BACKINGSTORE_LOCALMEM_CONTIG) != 0)
         {
-                       uDevVAddrAlignment = pBMHeap->sDevArena.ui32DataPageSize;
+            uDevVAddrAlignment = pBMHeap->sDevArena.ui32DataPageSize;
 
             if (uPSize % uDevVAddrAlignment != 0)
             {
                 PVR_DPF((PVR_DBG_ERROR, "Cannot use use this memory sharing workaround with allocations that might be suballocated"));
                 goto fail_mapping_alloc;
             }
-            uDevVAddrAlignment = 0; 
+            uDevVAddrAlignment = 0; /* FIXME: find out why it doesn't work if alignment is specified */
 
-            
+            /* If the user has specified heap CACHETYPE flags, use them to
+             * override the flags inherited from the heap.
+             */
             if (pMapping->ui32Flags & PVRSRV_HAP_CACHETYPE_MASK)
             {
                 ui32Attribs &= ~PVRSRV_HAP_CACHETYPE_MASK;
                 ui32Attribs |= (pMapping->ui32Flags & PVRSRV_HAP_CACHETYPE_MASK);
             }
 
-            
+            /* allocate "shared" pages. */
             if (XProcWorkaroundAllocShareable(pBMHeap->pLocalDevMemArena,
                                               ui32Attribs,
                                               (IMG_UINT32)uPSize,
                                               pBMHeap->sDevArena.ui32DataPageSize,
+                                                                                         pvPrivData,
+                                                                                         ui32PrivDataLength,
                                               (IMG_VOID **)&pMapping->CpuVAddr,
                                               &pMapping->hOSMemHandle) != PVRSRV_OK)
             {
@@ -2168,9 +2813,10 @@ BM_ImportMemory (IMG_VOID *pH,
                 goto fail_mapping_alloc;
             }
 
-            
-            
-
+            /* specify how page addresses are derived */
+            /* it works just like "env" now - no need to record
+               it as shareable, as we use the actual hOSMemHandle
+               and only divert to our wrapper layer based on Attribs */
             pMapping->eCpuMemoryOrigin = hm_env;
             bBadBackingStoreType = IMG_FALSE;
         }
@@ -2183,23 +2829,41 @@ BM_ImportMemory (IMG_VOID *pH,
        }
        else
 
-       
-
+       /*
+               What type of backing store do we have?
+       */
        if(pBMHeap->ui32Attribs & PVRSRV_BACKINGSTORE_SYSMEM_NONCONTIG)
        {
                IMG_UINT32 ui32Attribs = pBMHeap->ui32Attribs;
 
-               
+               /* The allocation code needs to know this is a sparse mapping */
+               if (pMapping->ui32Flags & PVRSRV_MEM_SPARSE)
+               {
+                       ui32Attribs |= PVRSRV_MEM_SPARSE;
+               }
+
+               /* If the user has specified heap CACHETYPE flags, use them to
+                * override the flags inherited from the heap.
+                */
                if (pMapping->ui32Flags & PVRSRV_HAP_CACHETYPE_MASK)
                {
                        ui32Attribs &= ~PVRSRV_HAP_CACHETYPE_MASK;
                        ui32Attribs |= (pMapping->ui32Flags & PVRSRV_HAP_CACHETYPE_MASK);
                }
-
                
+               if (pMapping->ui32Flags & PVRSRV_MEM_ALLOCATENONCACHEDMEM)
+               {
+                       ui32Attribs &= ~PVRSRV_MEM_ALLOCATENONCACHEDMEM;
+                       ui32Attribs |= (pMapping->ui32Flags & PVRSRV_MEM_ALLOCATENONCACHEDMEM);
+               }               
+               
+               /* allocate pages from the OS RAM */
                if (OSAllocPages(ui32Attribs,
                                                 uPSize,
                                                 pBMHeap->sDevArena.ui32DataPageSize,
+                                                pvPrivData,
+                                                ui32PrivDataLength,
+                                                pMapping,
                                                 (IMG_VOID **)&pMapping->CpuVAddr,
                                                 &pMapping->hOSMemHandle) != PVRSRV_OK)
                {
@@ -2209,7 +2873,7 @@ BM_ImportMemory (IMG_VOID *pH,
                        goto fail_mapping_alloc;
                }
 
-               
+               /* specify how page addresses are derived */
                pMapping->eCpuMemoryOrigin = hm_env;
        }
        else if(pBMHeap->ui32Attribs & PVRSRV_BACKINGSTORE_LOCALMEM_CONTIG)
@@ -2217,10 +2881,18 @@ BM_ImportMemory (IMG_VOID *pH,
                IMG_SYS_PHYADDR sSysPAddr;
                IMG_UINT32 ui32Attribs = pBMHeap->ui32Attribs;
 
-               
+               /* The allocation code needs to know this is a sparse mapping */
+               if (pMapping->ui32Flags & PVRSRV_MEM_SPARSE)
+               {
+                       ui32Attribs |= PVRSRV_MEM_SPARSE;
+               }
+
+               /* allocate pages from the local device memory allocator */
                PVR_ASSERT(pBMHeap->pLocalDevMemArena != IMG_NULL);
 
-               
+               /* If the user has specified heap CACHETYPE flags, use them to
+                * override the flags inherited from the heap.
+                */
                if (pMapping->ui32Flags & PVRSRV_HAP_CACHETYPE_MASK)
                {
                        ui32Attribs &= ~PVRSRV_HAP_CACHETYPE_MASK;
@@ -2234,17 +2906,20 @@ BM_ImportMemory (IMG_VOID *pH,
                                           0,
                                           pBMHeap->sDevArena.ui32DataPageSize,
                                           0,
+                                          pvPrivData,
+                                          ui32PrivDataLength,
                                           (IMG_UINTPTR_T *)&sSysPAddr.uiAddr))
                {
                        PVR_DPF((PVR_DBG_ERROR, "BM_ImportMemory: RA_Alloc(0x%x) FAILED", uPSize));
                        goto fail_mapping_alloc;
                }
 
-               
+               /* derive the CPU virtual address */
                pMapping->CpuPAddr = SysSysPAddrToCpuPAddr(sSysPAddr);
                if(OSReservePhys(pMapping->CpuPAddr,
                                                 uPSize,
                                                 ui32Attribs,
+                                                pMapping,
                                                 &pMapping->CpuVAddr,
                                                 &pMapping->hOSMemHandle) != PVRSRV_OK)
                {
@@ -2252,7 +2927,7 @@ BM_ImportMemory (IMG_VOID *pH,
                        goto fail_dev_mem_alloc;
                }
 
-               
+               /* specify how page addresses are derived */
                pMapping->eCpuMemoryOrigin = hm_contiguous;
        }
        else
@@ -2261,26 +2936,32 @@ BM_ImportMemory (IMG_VOID *pH,
                goto fail_mapping_alloc;
        }
 
-       
-       bResult = DevMemoryAlloc (pBMContext,
-                                                               pMapping,
-                                                               IMG_NULL,
-                                                               uFlags,
-                                                               (IMG_UINT32)uDevVAddrAlignment,
-                                                               &pMapping->DevVAddr);
-       if (!bResult)
+       /*
+        * Allocate some device memory for what we just allocated.
+        */
+       if ((uFlags & PVRSRV_MEM_SPARSE) == 0)
        {
-               PVR_DPF((PVR_DBG_ERROR,
-                               "BM_ImportMemory: DevMemoryAlloc(0x%x) failed",
-                               pMapping->uSize));
-               goto fail_dev_mem_alloc;
-       }
-
-       
+               bResult = DevMemoryAlloc (pBMContext,
+                                                                       pMapping,
+                                                                       IMG_NULL,
+                                                                       uFlags,
+                                                                       (IMG_UINT32)uDevVAddrAlignment,
+                                                                       &pMapping->DevVAddr);
+               if (!bResult)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,
+                                       "BM_ImportMemory: DevMemoryAlloc(0x%x) failed",
+                                       pMapping->uSize));
+                       goto fail_dev_mem_alloc;
+               }
        
-       PVR_ASSERT (uDevVAddrAlignment>1?(pMapping->DevVAddr.uiAddr%uDevVAddrAlignment)==0:1);
+               /* uDevVAddrAlignment is currently set to zero so QAC generates warning which we override */
+               /* PRQA S 3356,3358 1 */
+               PVR_ASSERT (uDevVAddrAlignment>1?(pMapping->DevVAddr.uiAddr%uDevVAddrAlignment)==0:1);
+               PVR_ASSERT(pBase);
+               *pBase = pMapping->DevVAddr.uiAddr;
+       }
 
-       *pBase = pMapping->DevVAddr.uiAddr;
        *ppsMapping = pMapping;
 
        PVR_DPF ((PVR_DBG_MESSAGE, "BM_ImportMemory: IMG_TRUE"));
@@ -2289,7 +2970,7 @@ BM_ImportMemory (IMG_VOID *pH,
 fail_dev_mem_alloc:
        if (pMapping && (pMapping->CpuVAddr || pMapping->hOSMemHandle))
        {
-               
+               /* the size is double the actual size for interleaved allocations */
                if(pMapping->ui32Flags & PVRSRV_MEM_INTERLEAVED)
                {
                        pMapping->uSize /= 2;
@@ -2333,12 +3014,28 @@ fail_dev_mem_alloc:
        }
 fail_mapping_alloc:
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_MAPPING), pMapping, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
 fail_exit:
        return IMG_FALSE;
 }
 
 
+/*!
+******************************************************************************
+
+       @Function   BM_FreeMemory
+
+       @Description    Free a block of pages previously allocated via
+                               BM_ImportMemory.
+
+       @Input      h - buffer manager handle, not the void type as dictated by
+                                                the generic nature of the resource allocator interface.
+       @Input      _base - base address of blocks to free.
+       @Input      psMapping - arbitrary user reference associated with the
+                                        underlying storage provided by BM_ImportMemory
+       @Return         None
+
+ *****************************************************************************/
 static IMG_VOID
 BM_FreeMemory (IMG_VOID *h, IMG_UINTPTR_T _base, BM_MAPPING *psMapping)
 {
@@ -2359,9 +3056,17 @@ BM_FreeMemory (IMG_VOID *h, IMG_UINTPTR_T _base, BM_MAPPING *psMapping)
                return;
        }
 
-       DevMemoryFree (psMapping);
+       /*
+               Only free the virtual memory if we got as far a allocating it.
+               This NULL check should be safe as we always have a guard page
+               at virtual address 0x00000000
+       */
+       if (psMapping->DevVAddr.uiAddr)
+       {
+               DevMemoryFree (psMapping);
+       }
 
-       
+       /* the size is double the actual for interleaved */
        if((psMapping->ui32Flags & PVRSRV_MEM_INTERLEAVED) != 0)
        {
                psMapping->uSize /= 2;
@@ -2404,13 +3109,30 @@ BM_FreeMemory (IMG_VOID *h, IMG_UINTPTR_T _base, BM_MAPPING *psMapping)
        }
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BM_MAPPING), psMapping, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        PVR_DPF((PVR_DBG_MESSAGE,
                        "..BM_FreeMemory (h=0x%x, base=0x%x)",
                        (IMG_UINTPTR_T)h, _base));
 }
 
+/*!
+******************************************************************************
+
+ @Function     BM_GetPhysPageAddr
+
+ @Description
+
+ @Input                psMemInfo
+
+ @Input                sDevVPageAddr
+
+ @Output       psDevPAddr
+
+ @Return       IMG_VOID
+
+******************************************************************************/
+
 IMG_VOID BM_GetPhysPageAddr(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
                                                                IMG_DEV_VIRTADDR sDevVPageAddr,
                                                                IMG_DEV_PHYADDR *psDevPAddr)
@@ -2419,12 +3141,12 @@ IMG_VOID BM_GetPhysPageAddr(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
 
        PVR_DPF((PVR_DBG_MESSAGE, "BM_GetPhysPageAddr"));
 
-       PVR_ASSERT (psMemInfo && psDevPAddr)
+       PVR_ASSERT(psMemInfo && psDevPAddr);
 
-       
+       /* check it's a page address */
        PVR_ASSERT((sDevVPageAddr.uiAddr & 0xFFF) == 0);
 
-        
+       /* PRQA S 0505 4 */ /* PVR_ASSERT should catch NULL ptrs */
        psDeviceNode = ((BM_BUF*)psMemInfo->sMemBlk.hBuffer)->pMapping->pBMHeap->pBMContext->psDeviceNode;
 
        *psDevPAddr = psDeviceNode->pfnMMUGetPhysPageAddr(((BM_BUF*)psMemInfo->sMemBlk.hBuffer)->pMapping->pBMHeap->pMMUHeap,
@@ -2432,6 +3154,16 @@ IMG_VOID BM_GetPhysPageAddr(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
 }
 
 
+/*!
+******************************************************************************
+ @Function     BM_GetMMUContext
+
+ @Description  utility function to return the MMU context
+
+ @Input     hDevMemHeap - the Dev mem heap handle
+
+ @Return       MMU context, else NULL
+**************************************************************************/
 MMU_CONTEXT* BM_GetMMUContext(IMG_HANDLE hDevMemHeap)
 {
        BM_HEAP *pBMHeap = (BM_HEAP*)hDevMemHeap;
@@ -2441,6 +3173,16 @@ MMU_CONTEXT* BM_GetMMUContext(IMG_HANDLE hDevMemHeap)
        return pBMHeap->pBMContext->psMMUContext;
 }
 
+/*!
+******************************************************************************
+ @Function     BM_GetMMUContextFromMemContext
+
+ @Description  utility function to return the MMU context
+
+ @Input     hDevMemContext - the Dev mem context handle
+
+ @Return       MMU context, else NULL
+**************************************************************************/
 MMU_CONTEXT* BM_GetMMUContextFromMemContext(IMG_HANDLE hDevMemContext)
 {
        BM_CONTEXT *pBMContext = (BM_CONTEXT*)hDevMemContext;
@@ -2450,6 +3192,16 @@ MMU_CONTEXT* BM_GetMMUContextFromMemContext(IMG_HANDLE hDevMemContext)
        return pBMContext->psMMUContext;
 }
 
+/*!
+******************************************************************************
+ @Function     BM_GetMMUHeap
+
+ @Description  utility function to return the MMU heap handle
+
+ @Input     hDevMemHeap - the Dev mem heap handle
+
+ @Return       MMU heap handle, else NULL
+**************************************************************************/
 IMG_HANDLE BM_GetMMUHeap(IMG_HANDLE hDevMemHeap)
 {
        PVR_DPF((PVR_DBG_VERBOSE, "BM_GetMMUHeap"));
@@ -2458,6 +3210,16 @@ IMG_HANDLE BM_GetMMUHeap(IMG_HANDLE hDevMemHeap)
 }
 
 
+/*!
+******************************************************************************
+ @Function     BM_GetDeviceNode
+
+ @Description  utility function to return the devicenode from the BM Context
+
+ @Input     hDevMemContext - the Dev Mem Context
+
+ @Return       MMU heap handle, else NULL
+**************************************************************************/
 PVRSRV_DEVICE_NODE* BM_GetDeviceNode(IMG_HANDLE hDevMemContext)
 {
        PVR_DPF((PVR_DBG_VERBOSE, "BM_GetDeviceNode"));
@@ -2466,6 +3228,16 @@ PVRSRV_DEVICE_NODE* BM_GetDeviceNode(IMG_HANDLE hDevMemContext)
 }
 
 
+/*!
+******************************************************************************
+ @Function     BM_GetMappingHandle
+
+ @Description  utility function to return the mapping handle from a meminfo
+
+ @Input     psMemInfo - kernel meminfo
+
+ @Return       mapping handle, else NULL
+**************************************************************************/
 IMG_HANDLE BM_GetMappingHandle(PVRSRV_KERNEL_MEM_INFO *psMemInfo)
 {
        PVR_DPF((PVR_DBG_VERBOSE, "BM_GetMappingHandle"));
@@ -2473,3 +3245,115 @@ IMG_HANDLE BM_GetMappingHandle(PVRSRV_KERNEL_MEM_INFO *psMemInfo)
        return ((BM_BUF*)psMemInfo->sMemBlk.hBuffer)->pMapping->hOSMemHandle;
 }
 
+/*!
+******************************************************************************
+ @Function     BM_MappingHandleFromBuffer
+
+ @Description  utility function to get the BM mapping handle from a BM buffer
+
+ @Input     hBuffer - Handle to BM buffer
+
+ @Return       BM mapping handle
+**************************************************************************/
+IMG_HANDLE BM_MappingHandleFromBuffer(IMG_HANDLE hBuffer)
+{
+       BM_BUF *psBuffer;
+
+       PVR_ASSERT(hBuffer != IMG_NULL);
+       psBuffer = hBuffer;
+       return psBuffer->pMapping;
+}
+
+/*!
+******************************************************************************
+ @Function     BM_GetVirtualSize
+
+ @Description  utility function to get the VM size of a BM mapping
+
+ @Input     hBMHandle - Handle to BM mapping
+
+ @Return       VM size of mapping
+**************************************************************************/
+IMG_UINT32 BM_GetVirtualSize(IMG_HANDLE hBMHandle)
+{
+       BM_MAPPING *psMapping;
+
+       PVR_ASSERT(hBMHandle != IMG_NULL);
+       psMapping = hBMHandle;
+       return psMapping->ui32ChunkSize * psMapping->ui32NumVirtChunks;
+}
+
+/*!
+******************************************************************************
+ @Function     BM_MapPageAtOffset
+
+ @Description  utility function check if the specificed offset in a BM mapping
+                is a page that needs tp be mapped
+
+ @Input     hBMHandle - Handle to BM mapping
+
+ @Input     ui32Offset - Offset into allocation
+
+ @Return       IMG_TRUE if the page should be mapped
+**************************************************************************/
+IMG_BOOL BM_MapPageAtOffset(IMG_HANDLE hBMHandle, IMG_UINT32 ui32Offset)
+{
+       BM_MAPPING *psMapping;
+       IMG_UINT32 ui32ChunkIndex;
+
+       PVR_ASSERT(hBMHandle != IMG_NULL);
+       psMapping = hBMHandle;
+
+       ui32ChunkIndex = ui32Offset / psMapping->ui32ChunkSize;
+       /* Check for overrun */
+       PVR_ASSERT(ui32ChunkIndex <= psMapping->ui32NumVirtChunks);
+       return psMapping->pabMapChunk[ui32ChunkIndex];
+}
+
+/*!
+******************************************************************************
+ @Function     BM_VirtOffsetToPhyscial
+
+ @Description  utility function find of physical offset of a sparse allocation
+                from it's virtual offset.
+
+ @Input     hBMHandle - Handle to BM mapping
+
+ @Input     ui32VirtOffset - Virtual offset into allocation
+ @Output    pui32PhysOffset - Physical offset
+
+ @Return       IMG_TRUE if the virtual offset is physically backed
+**************************************************************************/
+IMG_BOOL BM_VirtOffsetToPhysical(IMG_HANDLE hBMHandle,
+                                                                  IMG_UINT32 ui32VirtOffset,
+                                                                  IMG_UINT32 *pui32PhysOffset)
+{
+       BM_MAPPING *psMapping;
+       IMG_UINT32 ui32ChunkOffset;
+       IMG_UINT32 ui32PhysOffset = 0;
+       IMG_UINT32 i;
+
+       PVR_ASSERT(hBMHandle != IMG_NULL);
+       psMapping = hBMHandle;
+
+       ui32ChunkOffset = ui32VirtOffset / psMapping->ui32ChunkSize;
+       if (!psMapping->pabMapChunk[ui32ChunkOffset])
+       {
+               return IMG_FALSE;
+       }
+
+       for (i=0;i<ui32ChunkOffset;i++)
+       {
+               if (psMapping->pabMapChunk[i])
+               {
+                       ui32PhysOffset += psMapping->ui32ChunkSize;
+               }
+       }
+       *pui32PhysOffset = ui32PhysOffset;
+
+       return IMG_TRUE;
+}
+/******************************************************************************
+ End of file (buffer_manager.c)
+******************************************************************************/
index 4231d81..69e9deb 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device class services functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Kernel services functions for device class devices
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
 #include "buffer_manager.h"
@@ -45,17 +61,26 @@ void OSVSyncMISR(IMG_HANDLE, IMG_BOOL);
 IMG_VOID PVRSRVFreeCommandCompletePacketKM(IMG_HANDLE  hCmdCookie,
                                                                                   IMG_BOOL             bScheduleMISR);
 #endif
+/***********************************************************************
+       Local Display Class Structures
+************************************************************************/
 typedef struct PVRSRV_DC_SRV2DISP_KMJTABLE_TAG *PPVRSRV_DC_SRV2DISP_KMJTABLE;
 
+/*
+       Display Class Buffer Info
+*/
 typedef struct PVRSRV_DC_BUFFER_TAG
 {
-       
+       /* BC/DC common details - THIS MUST BE THE FIRST MEMBER */
        PVRSRV_DEVICECLASS_BUFFER sDeviceClassBuffer;
 
        struct PVRSRV_DISPLAYCLASS_INFO_TAG *psDCInfo;
        struct PVRSRV_DC_SWAPCHAIN_TAG *psSwapChain;
 } PVRSRV_DC_BUFFER;
 
+/*
+       Display Device Class kernel swapchain information structure
+*/
 typedef struct PVRSRV_DC_SWAPCHAIN_TAG
 {
        IMG_HANDLE                                                      hExtSwapChain;
@@ -68,11 +93,18 @@ typedef struct PVRSRV_DC_SWAPCHAIN_TAG
        PVRSRV_DC_BUFFER                                        *psLastFlipBuffer;
        IMG_UINT32                                                      ui32MinSwapInterval;
        IMG_UINT32                                                      ui32MaxSwapInterval;
+#if !defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED)
+       PVRSRV_KERNEL_SYNC_INFO                         **ppsLastSyncInfos;
+       IMG_UINT32                                                      ui32LastNumSyncInfos;
+#endif /* !defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED) */
        struct PVRSRV_DISPLAYCLASS_INFO_TAG *psDCInfo;
        struct PVRSRV_DC_SWAPCHAIN_TAG          *psNext;
 } PVRSRV_DC_SWAPCHAIN;
 
 
+/*
+       Display Device Class kernel swapchain referecne structure
+*/
 typedef struct PVRSRV_DC_SWAPCHAIN_REF_TAG
 {
        struct PVRSRV_DC_SWAPCHAIN_TAG          *psSwapChain;
@@ -80,6 +112,9 @@ typedef struct PVRSRV_DC_SWAPCHAIN_REF_TAG
 } PVRSRV_DC_SWAPCHAIN_REF;
 
 
+/*
+       Display Device Class kernel services information structure
+*/
 typedef struct PVRSRV_DISPLAYCLASS_INFO_TAG
 {
        IMG_UINT32                                                      ui32RefCount;
@@ -92,6 +127,9 @@ typedef struct PVRSRV_DISPLAYCLASS_INFO_TAG
 } PVRSRV_DISPLAYCLASS_INFO;
 
 
+/*
+       Per-context Display Device Class kernel services information structure
+*/
 typedef struct PVRSRV_DISPLAYCLASS_PERCONTEXT_INFO_TAG
 {
        PVRSRV_DISPLAYCLASS_INFO                        *psDCInfo;
@@ -99,17 +137,26 @@ typedef struct PVRSRV_DISPLAYCLASS_PERCONTEXT_INFO_TAG
 } PVRSRV_DISPLAYCLASS_PERCONTEXT_INFO;
 
 
+/***********************************************************************
+       Local Buffer Class Structures
+************************************************************************/
 typedef struct PVRSRV_BC_SRV2BUFFER_KMJTABLE_TAG *PPVRSRV_BC_SRV2BUFFER_KMJTABLE;
 
+/*
+       Buffer Class Buffer Info
+*/
 typedef struct PVRSRV_BC_BUFFER_TAG
 {
-       
+       /* BC/DC common details - THIS MUST BE THE FIRST MEMBER */
        PVRSRV_DEVICECLASS_BUFFER sDeviceClassBuffer;
 
        struct PVRSRV_BUFFERCLASS_INFO_TAG *psBCInfo;
 } PVRSRV_BC_BUFFER;
 
 
+/*
+       Buffer Device Class kernel services information structure
+*/
 typedef struct PVRSRV_BUFFERCLASS_INFO_TAG
 {
        IMG_UINT32                                                      ui32RefCount;
@@ -117,13 +164,16 @@ typedef struct PVRSRV_BUFFERCLASS_INFO_TAG
        IMG_HANDLE                                                      hExtDevice;
        PPVRSRV_BC_SRV2BUFFER_KMJTABLE          psFuncTable;
        IMG_HANDLE                                                      hDevMemContext;
-       
+       /* buffer info returned from 3rd party driver */
        IMG_UINT32                                                      ui32BufferCount;
        PVRSRV_BC_BUFFER                                        *psBuffer;
 
 } PVRSRV_BUFFERCLASS_INFO;
 
 
+/*
+       Per-context Buffer Device Class kernel services information structure
+*/
 typedef struct PVRSRV_BUFFERCLASS_PERCONTEXT_INFO_TAG
 {
        PVRSRV_BUFFERCLASS_INFO                         *psBCInfo;
@@ -131,6 +181,21 @@ typedef struct PVRSRV_BUFFERCLASS_PERCONTEXT_INFO_TAG
 } PVRSRV_BUFFERCLASS_PERCONTEXT_INFO;
 
 
+/*!
+******************************************************************************
+ @Function     DCDeviceHandleToDCInfo
+
+ @Description
+
+ Convert a client-visible 3rd party device class handle to an internal
+ PVRSRV_DISPLAYCLASS_INFO pointer.
+
+ @Input hDeviceKM      - handle to display class device, returned from OpenDCDevice
+
+ @Return
+       success: pointer to PVRSRV_DISPLAYCLASS_INFO
+       failure: IMG_NULL
+******************************************************************************/
 static PVRSRV_DISPLAYCLASS_INFO* DCDeviceHandleToDCInfo (IMG_HANDLE hDeviceKM)
 {
        PVRSRV_DISPLAYCLASS_PERCONTEXT_INFO *psDCPerContextInfo;
@@ -141,6 +206,21 @@ static PVRSRV_DISPLAYCLASS_INFO* DCDeviceHandleToDCInfo (IMG_HANDLE hDeviceKM)
 }
 
 
+/*!
+******************************************************************************
+ @Function     BCDeviceHandleToBCInfo
+
+ @Description
+
+ Convert a client-visible 3rd party buffer class handle to an internal
+ PVRSRV_BUFFERCLASS_INFO pointer.
+
+ @Input hDeviceKM      - handle to buffer class device, returned from OpenBCDevice
+
+ @Return
+       success: pointer to PVRSRV_BUFFERCLASS_INFO
+       failure: IMG_NULL
+******************************************************************************/
 static PVRSRV_BUFFERCLASS_INFO* BCDeviceHandleToBCInfo (IMG_HANDLE hDeviceKM)
 {
        PVRSRV_BUFFERCLASS_PERCONTEXT_INFO *psBCPerContextInfo;
@@ -150,6 +230,20 @@ static PVRSRV_BUFFERCLASS_INFO* BCDeviceHandleToBCInfo (IMG_HANDLE hDeviceKM)
        return psBCPerContextInfo->psBCInfo;
 }
 
+/*!
+******************************************************************************
+ @Function     PVRSRVEnumerateDCKM_ForEachVaCb
+
+ @Description
+
+ Enumerates the device node (if is of the same class as given).
+
+ @Input psDeviceNode   - The device node to be enumerated
+               va                              - variable arguments list, with:
+                                                       pui32DevCount   - The device count pointer (to be increased)
+                                                       ppui32DevID             - The pointer to the device IDs pointer (to be updated and increased)
+                                                       peDeviceClass   - The pointer to the device class of the psDeviceNode's to be enumerated.
+******************************************************************************/
 static IMG_VOID PVRSRVEnumerateDCKM_ForEachVaCb(PVRSRV_DEVICE_NODE *psDeviceNode, va_list va)
 {
        IMG_UINT *pui32DevCount;
@@ -172,18 +266,40 @@ static IMG_VOID PVRSRVEnumerateDCKM_ForEachVaCb(PVRSRV_DEVICE_NODE *psDeviceNode
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVEnumerateDCKM
+
+ @Description
+
+ Enumerates devices available in a given class.
+ On first call, pass valid ptr for pui32DevCount and IMG_NULL for pui32DevID,
+ On second call, pass same ptr for pui32DevCount and client allocated ptr
+ for pui32DevID device id list
+
+ @Input hServices              - handle for services connection
+ @Input ui32DevClass   - device class identifier
+ @Output pui32DevCount - number of devices available in class
+ @Output pui32DevID            - list of device ids in the device class
+
+ @Return
+       success: handle to matching display class device
+       failure: IMG_NULL
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVEnumerateDCKM (PVRSRV_DEVICE_CLASS DeviceClass,
                                                                  IMG_UINT32 *pui32DevCount,
                                                                  IMG_UINT32 *pui32DevID )
 {
-       
+       /*PVRSRV_DEVICE_NODE    *psDeviceNode;*/
        IMG_UINT                        ui32DevCount = 0;
        SYS_DATA                        *psSysData;
 
        SysAcquireData(&psSysData);
 
-       
+       /* search devonode list for devices in specified class and return the device ids */
        List_PVRSRV_DEVICE_NODE_ForEach_va(psSysData->psDeviceNodeList,
                                                                                &PVRSRVEnumerateDCKM_ForEachVaCb,
                                                                                &ui32DevCount,
@@ -204,35 +320,55 @@ PVRSRV_ERROR PVRSRVEnumerateDCKM (PVRSRV_DEVICE_CLASS DeviceClass,
 }
 
 
-static
-PVRSRV_ERROR PVRSRVRegisterDCDeviceKM (PVRSRV_DC_SRV2DISP_KMJTABLE *psFuncTable,
-                                                                          IMG_UINT32 *pui32DeviceID)
-{
-       PVRSRV_DISPLAYCLASS_INFO        *psDCInfo = IMG_NULL;
-       PVRSRV_DEVICE_NODE                      *psDeviceNode;
-       SYS_DATA                                        *psSysData;
-
-       
-
-
+/*!
+******************************************************************************
 
+ @Function     PVRSRVRegisterDCDeviceKM
 
+ @Description
 
+ registers an external device with the system
 
+ @Input                psFuncTable             : device function table
 
+ @Output       pui32DeviceID   : unique device key (for case of multiple identical devices)
 
+ @Return       PVRSRV_ERROR    :
 
+******************************************************************************/
+static
+PVRSRV_ERROR PVRSRVRegisterDCDeviceKM (PVRSRV_DC_SRV2DISP_KMJTABLE *psFuncTable,
+                                                                          IMG_UINT32 *pui32DeviceID)
+{
+       PVRSRV_DISPLAYCLASS_INFO        *psDCInfo = IMG_NULL;
+       PVRSRV_DEVICE_NODE                      *psDeviceNode;
+       SYS_DATA                                        *psSysData;
 
+       /*
+               IN:
+                - name of client side ext. device driver library for subsequent loading
+                - predefined list of callbacks into kernel ext. device driver (based on class type)
 
+               FUNCTION TASKS:
+                - allocate display device class info structure
+                - hang ext.device kernel callbacks on this structure (pfnKSwapToSystem)
 
+               OUT:
+                - DEVICE_ID
+                - pass back devinfo? no
 
+               Q&A:
+                - DEVICE_ID passed in or allocated - assume allocate
+       */
 
        SysAcquireData(&psSysData);
 
-       
-
+       /*
+               If we got this far we're doing dynamic enumeration
+               or first time static registration
+       */
 
-       
+       /* Allocate device control block */
        if(OSAllocMem( PVRSRV_OS_PAGEABLE_HEAP,
                                         sizeof(*psDCInfo),
                                         (IMG_VOID **)&psDCInfo, IMG_NULL,
@@ -243,7 +379,7 @@ PVRSRV_ERROR PVRSRVRegisterDCDeviceKM (PVRSRV_DC_SRV2DISP_KMJTABLE *psFuncTable,
        }
        OSMemSet (psDCInfo, 0, sizeof(*psDCInfo));
 
-       
+       /* setup the display device information structure */
        if(OSAllocMem( PVRSRV_OS_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_DC_SRV2DISP_KMJTABLE),
                                         (IMG_VOID **)&psDCInfo->psFuncTable, IMG_NULL,
@@ -254,10 +390,10 @@ PVRSRV_ERROR PVRSRVRegisterDCDeviceKM (PVRSRV_DC_SRV2DISP_KMJTABLE *psFuncTable,
        }
        OSMemSet (psDCInfo->psFuncTable, 0, sizeof(PVRSRV_DC_SRV2DISP_KMJTABLE));
 
-       
+       /* copy the jump table */
        *psDCInfo->psFuncTable = *psFuncTable;
 
-       
+       /* Allocate device node */
        if(OSAllocMem( PVRSRV_OS_NON_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_DEVICE_NODE),
                                         (IMG_VOID **)&psDeviceNode, IMG_NULL,
@@ -275,7 +411,7 @@ PVRSRV_ERROR PVRSRVRegisterDCDeviceKM (PVRSRV_DC_SRV2DISP_KMJTABLE *psFuncTable,
        psDeviceNode->sDevId.eDeviceClass = PVRSRV_DEVICE_CLASS_DISPLAY;
        psDeviceNode->psSysData = psSysData;
 
-       
+       /* allocate a unique device id */
        if (AllocateDeviceID(psSysData, &psDeviceNode->sDevId.ui32DeviceIndex) != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVRegisterBCDeviceKM: Failed to allocate Device ID"));
@@ -287,10 +423,10 @@ PVRSRV_ERROR PVRSRVRegisterDCDeviceKM (PVRSRV_DC_SRV2DISP_KMJTABLE *psFuncTable,
                *pui32DeviceID = psDeviceNode->sDevId.ui32DeviceIndex;
        }
 
-       
+       /* Register the device with the system */
        SysRegisterExternalDevice(psDeviceNode);
 
-       
+       /* and finally insert the device into the dev-list */
        List_PVRSRV_DEVICE_NODE_Insert(&psSysData->psDeviceNodeList, psDeviceNode);
 
        return PVRSRV_OK;
@@ -304,11 +440,25 @@ ErrorExit:
        }
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DISPLAYCLASS_INFO), psDCInfo, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
 
        return PVRSRV_ERROR_OUT_OF_MEMORY;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRemoveDCDeviceKM
+
+ @Description
+
+ Removes external device from services system record
+
+ @Input           ui32DeviceIndex              : unique device key (for case of multiple identical devices)
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 static PVRSRV_ERROR PVRSRVRemoveDCDeviceKM(IMG_UINT32 ui32DevIndex)
 {
        SYS_DATA                                        *psSysData;
@@ -317,7 +467,7 @@ static PVRSRV_ERROR PVRSRVRemoveDCDeviceKM(IMG_UINT32 ui32DevIndex)
 
        SysAcquireData(&psSysData);
 
-       
+       /*search the node matching the devindex and display class*/
        psDeviceNode = (PVRSRV_DEVICE_NODE*)
                List_PVRSRV_DEVICE_NODE_Any_va(psSysData->psDeviceNodeList,
                                                                           &MatchDeviceKM_AnyVaCb,
@@ -326,37 +476,40 @@ static PVRSRV_ERROR PVRSRVRemoveDCDeviceKM(IMG_UINT32 ui32DevIndex)
                                                                           PVRSRV_DEVICE_CLASS_DISPLAY);
        if (!psDeviceNode)
        {
-               
+               /*device not found*/
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVRemoveDCDeviceKM: requested device %d not present", ui32DevIndex));
                return PVRSRV_ERROR_NO_DEVICENODE_FOUND;
        }
 
-       
+       /* setup DCInfo ptr */
        psDCInfo = (PVRSRV_DISPLAYCLASS_INFO*)psDeviceNode->pvDevice;
 
-       
-
-
+       /*
+               The device can only be removed if there are
+               no open connections in the Services interface
+       */
        if(psDCInfo->ui32RefCount == 0)
        {
-               
-
+               /*
+                       Remove from the device list.
+               */
                List_PVRSRV_DEVICE_NODE_Remove(psDeviceNode);
 
-               
+               /* Unregister the device with the system */
                SysRemoveExternalDevice(psDeviceNode);
 
-               
-
-
+               /*
+                       OK found a device with a matching devindex
+                       remove registration information
+               */
                PVR_ASSERT(psDCInfo->ui32RefCount == 0);
                (IMG_VOID)FreeDeviceID(psSysData, ui32DevIndex);
                (IMG_VOID)OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DC_SRV2DISP_KMJTABLE), psDCInfo->psFuncTable, IMG_NULL);
                psDCInfo->psFuncTable = IMG_NULL;
                (IMG_VOID)OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DISPLAYCLASS_INFO), psDCInfo, IMG_NULL);
-               
+               /*not nulling original pointer, overwritten*/
                (IMG_VOID)OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DEVICE_NODE), psDeviceNode, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
        }
        else
        {
@@ -368,6 +521,21 @@ static PVRSRV_ERROR PVRSRVRemoveDCDeviceKM(IMG_UINT32 ui32DevIndex)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRegisterBCDeviceKM
+
+ @Description
+
+ registers an external device with the system
+
+ @Input                psFuncTable             : device function table
+ @Input                ui32DeviceIndex         : unique device key (for case of multiple identical devices)
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 static
 PVRSRV_ERROR PVRSRVRegisterBCDeviceKM (PVRSRV_BC_SRV2BUFFER_KMJTABLE *psFuncTable,
                                                                           IMG_UINT32   *pui32DeviceID)
@@ -375,26 +543,30 @@ PVRSRV_ERROR PVRSRVRegisterBCDeviceKM (PVRSRV_BC_SRV2BUFFER_KMJTABLE *psFuncTabl
        PVRSRV_BUFFERCLASS_INFO *psBCInfo = IMG_NULL;
        PVRSRV_DEVICE_NODE              *psDeviceNode;
        SYS_DATA                                *psSysData;
-       
-
-
-
-
-
-
-
-
-
+       /*
+               IN:
+                - name of client side ext. device driver library for subsequent loading
+                - predefined list of callbacks into kernel ext. device driver (based on class type)
 
+               FUNCTION TASKS:
+                - allocate buffer device class info structure
 
+               OUT:
+                - DEVICE_ID
+                - pass back devinfo? no
 
+               Q&A:
+                - DEVICE_ID passed in or allocated - assume allcoate
+       */
 
        SysAcquireData(&psSysData);
 
-       
-
+       /*
+               If we got this far we're doing dynamic enumeration
+               or first time static registration
+       */
 
-       
+       /* Allocate device control block */
        if(OSAllocMem( PVRSRV_OS_PAGEABLE_HEAP,
                                         sizeof(*psBCInfo),
                                         (IMG_VOID **)&psBCInfo, IMG_NULL,
@@ -405,7 +577,7 @@ PVRSRV_ERROR PVRSRVRegisterBCDeviceKM (PVRSRV_BC_SRV2BUFFER_KMJTABLE *psFuncTabl
        }
        OSMemSet (psBCInfo, 0, sizeof(*psBCInfo));
 
-       
+       /* setup the buffer device information structure */
        if(OSAllocMem( PVRSRV_OS_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_BC_SRV2BUFFER_KMJTABLE),
                                         (IMG_VOID **)&psBCInfo->psFuncTable, IMG_NULL,
@@ -416,10 +588,10 @@ PVRSRV_ERROR PVRSRVRegisterBCDeviceKM (PVRSRV_BC_SRV2BUFFER_KMJTABLE *psFuncTabl
        }
        OSMemSet (psBCInfo->psFuncTable, 0, sizeof(PVRSRV_BC_SRV2BUFFER_KMJTABLE));
 
-       
+       /* copy the jump table */
        *psBCInfo->psFuncTable = *psFuncTable;
 
-       
+       /* Allocate device node */
        if(OSAllocMem( PVRSRV_OS_NON_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_DEVICE_NODE),
                                         (IMG_VOID **)&psDeviceNode, IMG_NULL,
@@ -437,7 +609,7 @@ PVRSRV_ERROR PVRSRVRegisterBCDeviceKM (PVRSRV_BC_SRV2BUFFER_KMJTABLE *psFuncTabl
        psDeviceNode->sDevId.eDeviceClass = PVRSRV_DEVICE_CLASS_BUFFER;
        psDeviceNode->psSysData = psSysData;
 
-       
+       /* allocate a unique device id */
        if (AllocateDeviceID(psSysData, &psDeviceNode->sDevId.ui32DeviceIndex) != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVRegisterBCDeviceKM: Failed to allocate Device ID"));
@@ -449,7 +621,7 @@ PVRSRV_ERROR PVRSRVRegisterBCDeviceKM (PVRSRV_BC_SRV2BUFFER_KMJTABLE *psFuncTabl
                *pui32DeviceID = psDeviceNode->sDevId.ui32DeviceIndex;
        }
 
-       
+       /* and finally insert the device into the dev-list */
        List_PVRSRV_DEVICE_NODE_Insert(&psSysData->psDeviceNodeList, psDeviceNode);
 
        return PVRSRV_OK;
@@ -463,12 +635,26 @@ ErrorExit:
        }
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_BUFFERCLASS_INFO), psBCInfo, IMG_NULL);
-       
+       /*not nulling shared pointer, wasn't allocated to this point*/
 
        return PVRSRV_ERROR_OUT_OF_MEMORY;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRemoveBCDeviceKM
+
+ @Description
+
+ Removes external device from services system record
+
+ @Input           ui32DeviceIndex              : unique device key (for case of multiple identical devices)
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 static PVRSRV_ERROR PVRSRVRemoveBCDeviceKM(IMG_UINT32 ui32DevIndex)
 {
        SYS_DATA                                        *psSysData;
@@ -477,7 +663,7 @@ static PVRSRV_ERROR PVRSRVRemoveBCDeviceKM(IMG_UINT32 ui32DevIndex)
 
        SysAcquireData(&psSysData);
 
-       
+       /*search the device node with the devindex and buffer class*/
        psDevNode = (PVRSRV_DEVICE_NODE*)
                List_PVRSRV_DEVICE_NODE_Any_va(psSysData->psDeviceNodeList,
                                                                           &MatchDeviceKM_AnyVaCb,
@@ -491,31 +677,33 @@ static PVRSRV_ERROR PVRSRVRemoveBCDeviceKM(IMG_UINT32 ui32DevIndex)
                return PVRSRV_ERROR_NO_DEVICENODE_FOUND;
        }
 
-       
-       
+       /* set-up devnode ptr */
+/*     psDevNode = *(ppsDevNode); */
+       /* setup BCInfo ptr */
        psBCInfo = (PVRSRV_BUFFERCLASS_INFO*)psDevNode->pvDevice;
 
-       
-
-
+       /*
+               The device can only be removed if there are
+               no open connections in the Services interface
+       */
        if(psBCInfo->ui32RefCount == 0)
        {
-               
-
+               /*
+                       Remove from the device list.
+               */
                List_PVRSRV_DEVICE_NODE_Remove(psDevNode);
 
-               
-
-
+               /*
+                       OK found a device with a matching devindex
+                       remove registration information
+               */
                (IMG_VOID)FreeDeviceID(psSysData, ui32DevIndex);
-               
-               
                (IMG_VOID)OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_BC_SRV2BUFFER_KMJTABLE), psBCInfo->psFuncTable, IMG_NULL);
                psBCInfo->psFuncTable = IMG_NULL;
                (IMG_VOID)OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_BUFFERCLASS_INFO), psBCInfo, IMG_NULL);
-               
+               /*not nulling pointer, copy on stack*/
                (IMG_VOID)OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DEVICE_NODE), psDevNode, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
        }
        else
        {
@@ -528,18 +716,29 @@ static PVRSRV_ERROR PVRSRVRemoveBCDeviceKM(IMG_UINT32 ui32DevIndex)
 
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVCloseDCDeviceKM
+
+ @Description
+
+ Closes a connection to the Display Class device
+
+ @Input           hDeviceKM            : device handle
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
-PVRSRV_ERROR PVRSRVCloseDCDeviceKM (IMG_HANDLE hDeviceKM,
-                                                                       IMG_BOOL        bResManCallback)
+PVRSRV_ERROR PVRSRVCloseDCDeviceKM (IMG_HANDLE hDeviceKM)
 {
        PVRSRV_ERROR eError;
        PVRSRV_DISPLAYCLASS_PERCONTEXT_INFO *psDCPerContextInfo;
 
-       PVR_UNREFERENCED_PARAMETER(bResManCallback);
-
        psDCPerContextInfo = (PVRSRV_DISPLAYCLASS_PERCONTEXT_INFO *)hDeviceKM;
 
-       
+       /* Remove the item from the resman list and trigger the callback. */
        eError = ResManFreeResByPtr(psDCPerContextInfo->hResItem, CLEANUP_WITH_POLL);
 
        return eError;
@@ -561,38 +760,49 @@ static PVRSRV_ERROR CloseDCDeviceCallBack(IMG_PVOID  pvParam,
 
        if(psDCInfo->sSystemBuffer.sDeviceClassBuffer.ui32MemMapRefCount != 0)
        {
-               PVR_DPF((PVR_DBG_ERROR,"CloseDCDeviceCallBack: system buffer (0x%p) still mapped (refcount = %d)",
+               PVR_DPF((PVR_DBG_MESSAGE,"CloseDCDeviceCallBack: system buffer (0x%p) still mapped (refcount = %d)",
                                &psDCInfo->sSystemBuffer.sDeviceClassBuffer,
                                psDCInfo->sSystemBuffer.sDeviceClassBuffer.ui32MemMapRefCount));
-
-#if 0
-               
-               return PVRSRV_ERROR_STILL_MAPPED;
-#endif
        }
 
        psDCInfo->ui32RefCount--;
        if(psDCInfo->ui32RefCount == 0)
        {
-               
+               /* close the external device */
                psDCInfo->psFuncTable->pfnCloseDCDevice(psDCInfo->hExtDevice);
 
-               if (--psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo->ui32RefCount == 0)
-               {
-                       PVRSRVFreeSyncInfoKM(psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo);
-               }
+               PVRSRVKernelSyncInfoDecRef(psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo, IMG_NULL);
 
                psDCInfo->hDevMemContext = IMG_NULL;
                psDCInfo->hExtDevice = IMG_NULL;
        }
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DISPLAYCLASS_PERCONTEXT_INFO), psDCPerContextInfo, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVOpenDCDeviceKM
+
+ @Description
+
+ Opens a connection to the Display Class device, associating the connection
+ with a Device Memory Context for a services managed device
+
+ @Input           psPerProc            : Per-process data
+ @Input           ui32DeviceID         : unique device index
+ @Input           hDevCookie           : devcookie used to derive the Device Memory
+                                                               Context into BC surfaces will be mapped into
+ @Outut           phDeviceKM           : handle to the DC device
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVOpenDCDeviceKM (PVRSRV_PER_PROCESS_DATA     *psPerProc,
                                                                   IMG_UINT32                           ui32DeviceID,
@@ -613,7 +823,7 @@ PVRSRV_ERROR PVRSRVOpenDCDeviceKM (PVRSRV_PER_PROCESS_DATA  *psPerProc,
 
        SysAcquireData(&psSysData);
 
-       
+       /* find the matching devicenode */
        psDeviceNode = (PVRSRV_DEVICE_NODE*)
                        List_PVRSRV_DEVICE_NODE_Any_va(psSysData->psDeviceNodeList,
                                                                                   &MatchDeviceKM_AnyVaCb,
@@ -627,9 +837,10 @@ PVRSRV_ERROR PVRSRVOpenDCDeviceKM (PVRSRV_PER_PROCESS_DATA *psPerProc,
        }
        psDCInfo = (PVRSRV_DISPLAYCLASS_INFO*)psDeviceNode->pvDevice;
 
-       
-
-
+       /*
+               Allocate the per-context DC Info before calling the external device,
+               to make error handling easier.
+       */
        if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                  sizeof(*psDCPerContextInfo),
                                  (IMG_VOID **)&psDCPerContextInfo, IMG_NULL,
@@ -645,10 +856,10 @@ PVRSRV_ERROR PVRSRVOpenDCDeviceKM (PVRSRV_PER_PROCESS_DATA        *psPerProc,
 
                psDeviceNode = (PVRSRV_DEVICE_NODE *)hDevCookie;
 
-               
+               /* store the device kernel context to map into */
                psDCInfo->hDevMemContext = (IMG_HANDLE)psDeviceNode->sDevMemoryInfo.pBMKernelContext;
 
-               
+               /* create a syncinfo for the device's system surface */
                eError = PVRSRVAllocSyncInfoKM(IMG_NULL,
                                                                        (IMG_HANDLE)psDeviceNode->sDevMemoryInfo.pBMKernelContext,
                                                                        &psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo);
@@ -659,7 +870,7 @@ PVRSRV_ERROR PVRSRVOpenDCDeviceKM (PVRSRV_PER_PROCESS_DATA  *psPerProc,
                        return eError;
                }
 
-               
+               /* open the external device */
                eError = psDCInfo->psFuncTable->pfnOpenDCDevice(ui32DeviceID,
                                                                &psDCInfo->hExtDevice,
                                                                (PVRSRV_SYNC_DATA*)psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo->psSyncDataMemInfoKM->pvLinAddrKM);
@@ -667,28 +878,55 @@ PVRSRV_ERROR PVRSRVOpenDCDeviceKM (PVRSRV_PER_PROCESS_DATA        *psPerProc,
                {
                        PVR_DPF((PVR_DBG_ERROR,"PVRSRVOpenDCDeviceKM: Failed to open external DC device"));
                        psDCInfo->ui32RefCount--;
-                       PVRSRVFreeSyncInfoKM(psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo);
+                       PVRSRVKernelSyncInfoDecRef(psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo, IMG_NULL);
                        return eError;
                }
 
-               psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo->ui32RefCount++;
+               psDCPerContextInfo->psDCInfo = psDCInfo;
+               eError = PVRSRVGetDCSystemBufferKM(psDCPerContextInfo, IMG_NULL);
+               if(eError != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,"PVRSRVOpenDCDeviceKM: Failed to get system buffer"));
+                       psDCInfo->ui32RefCount--;
+                       PVRSRVKernelSyncInfoDecRef(psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo, IMG_NULL);
+                       return eError;
+               }
                psDCInfo->sSystemBuffer.sDeviceClassBuffer.ui32MemMapRefCount = 0;
        }
+       else
+       {
+               psDCPerContextInfo->psDCInfo = psDCInfo;
+       }
 
-       psDCPerContextInfo->psDCInfo = psDCInfo;
        psDCPerContextInfo->hResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                                                         RESMAN_TYPE_DISPLAYCLASS_DEVICE,
                                                                                                         psDCPerContextInfo,
                                                                                                         0,
                                                                                                         &CloseDCDeviceCallBack);
 
-       
+       /* return a reference to the DCPerContextInfo */
        *phDeviceKM = (IMG_HANDLE)psDCPerContextInfo;
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVEnumDCFormatsKM
+
+ @Description
+
+ Enumerates the devices pixel formats
+
+ @Input           hDeviceKM            : device handle
+ @Output   pui32Count          : number of pixel formats
+ @Output   psFormat                    : format list
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVEnumDCFormatsKM (IMG_HANDLE hDeviceKM,
                                                                        IMG_UINT32 *pui32Count,
@@ -704,12 +942,29 @@ PVRSRV_ERROR PVRSRVEnumDCFormatsKM (IMG_HANDLE hDeviceKM,
 
        psDCInfo = DCDeviceHandleToDCInfo(hDeviceKM);
 
-       
+       /* call into the display device driver to get info */
        return psDCInfo->psFuncTable->pfnEnumDCFormats(psDCInfo->hExtDevice, pui32Count, psFormat);
 }
 
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVEnumDCDimsKM
+
+ @Description
+
+ Enumerates the devices mode dimensions for a given pixel format
+
+ @Input           hDeviceKM            : device handle
+ @Input           psFormat                     : pixel format
+ @Output   pui32Count          : number of dimensions
+ @Output   psDim                       : dimensions list
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVEnumDCDimsKM (IMG_HANDLE hDeviceKM,
                                                                 DISPLAY_FORMAT *psFormat,
@@ -718,7 +973,7 @@ PVRSRV_ERROR PVRSRVEnumDCDimsKM (IMG_HANDLE hDeviceKM,
 {
        PVRSRV_DISPLAYCLASS_INFO *psDCInfo;
 
-       if(!hDeviceKM || !pui32Count || !psFormat)      
+       if(!hDeviceKM || !pui32Count || !psFormat)      //  psDim==NULL to query number of dims
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVEnumDCDimsKM: Invalid parameters"));
                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -726,11 +981,26 @@ PVRSRV_ERROR PVRSRVEnumDCDimsKM (IMG_HANDLE hDeviceKM,
 
        psDCInfo = DCDeviceHandleToDCInfo(hDeviceKM);
 
-       
+       /* call into the display device driver to get info */
        return psDCInfo->psFuncTable->pfnEnumDCDims(psDCInfo->hExtDevice, psFormat, pui32Count, psDim);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVGetDCSystemBufferKM
+
+ @Description
+
+ Get the primary surface and optionally return its buffer handle
+
+ @Input           hDeviceKM            : device handle
+ @Output   phBuffer                    : Optional buffer handle
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVGetDCSystemBufferKM (IMG_HANDLE hDeviceKM,
                                                                                IMG_HANDLE *phBuffer)
@@ -739,7 +1009,7 @@ PVRSRV_ERROR PVRSRVGetDCSystemBufferKM (IMG_HANDLE hDeviceKM,
        PVRSRV_DISPLAYCLASS_INFO *psDCInfo;
        IMG_HANDLE hExtBuffer;
 
-       if(!hDeviceKM || !phBuffer)
+       if(!hDeviceKM)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVGetDCSystemBufferKM: Invalid parameters"));
                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -747,7 +1017,7 @@ PVRSRV_ERROR PVRSRVGetDCSystemBufferKM (IMG_HANDLE hDeviceKM,
 
        psDCInfo = DCDeviceHandleToDCInfo(hDeviceKM);
 
-       
+       /* call into the display device driver to get info */
        eError = psDCInfo->psFuncTable->pfnGetDCSystemBuffer(psDCInfo->hExtDevice, &hExtBuffer);
        if(eError != PVRSRV_OK)
        {
@@ -755,7 +1025,7 @@ PVRSRV_ERROR PVRSRVGetDCSystemBufferKM (IMG_HANDLE hDeviceKM,
                return eError;
        }
 
-       
+       /* save the new info */
        psDCInfo->sSystemBuffer.sDeviceClassBuffer.pfnGetBufferAddr = psDCInfo->psFuncTable->pfnGetBufferAddr;
        psDCInfo->sSystemBuffer.sDeviceClassBuffer.hDevMemContext = psDCInfo->hDevMemContext;
        psDCInfo->sSystemBuffer.sDeviceClassBuffer.hExtDevice = psDCInfo->hExtDevice;
@@ -763,13 +1033,30 @@ PVRSRV_ERROR PVRSRVGetDCSystemBufferKM (IMG_HANDLE hDeviceKM,
 
        psDCInfo->sSystemBuffer.psDCInfo = psDCInfo;
 
-       
-       *phBuffer = (IMG_HANDLE)&(psDCInfo->sSystemBuffer);
+       /* return handle */
+       if (phBuffer)
+       {
+               *phBuffer = (IMG_HANDLE)&(psDCInfo->sSystemBuffer);
+       }
 
        return PVRSRV_OK;
 }
 
 
+/******************************************************************************
+
+ @Function     PVRSRVGetDCInfoKM
+
+ @Description
+
+ Gets Display Class device Info
+
+ @Input                hDeviceKM               : device handle
+ @Output       psDisplayInfo
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVGetDCInfoKM (IMG_HANDLE hDeviceKM,
                                                                DISPLAY_INFO *psDisplayInfo)
@@ -785,7 +1072,7 @@ PVRSRV_ERROR PVRSRVGetDCInfoKM (IMG_HANDLE hDeviceKM,
 
        psDCInfo = DCDeviceHandleToDCInfo(hDeviceKM);
 
-       
+       /* call into the display device driver to get info */
        eError = psDCInfo->psFuncTable->pfnGetDCInfo(psDCInfo->hExtDevice, psDisplayInfo);
        if (eError != PVRSRV_OK)
        {
@@ -827,7 +1114,7 @@ static PVRSRV_ERROR DestroyDCSwapChain(PVRSRV_DC_SWAPCHAIN *psSwapChain)
        PVRSRV_DISPLAYCLASS_INFO        *psDCInfo = psSwapChain->psDCInfo;
        IMG_UINT32 i;
 
-       
+       /* Update shared swapchains list */
        if( psDCInfo->psDCSwapChainShared )
        {
                if( psDCInfo->psDCSwapChainShared == psSwapChain )
@@ -851,10 +1138,10 @@ static PVRSRV_ERROR DestroyDCSwapChain(PVRSRV_DC_SWAPCHAIN *psSwapChain)
                }
        }
 
-       
+       /* Destroy command queue before swapchain - it may use the swapchain when commands are flushed. */
        PVRSRVDestroyCommandQueueKM(psSwapChain->psQueue);
 
-       
+       /* call into the display device driver to destroy a swapchain */
        eError = psDCInfo->psFuncTable->pfnDestroyDCSwapChain(psDCInfo->hExtDevice,
                                                                                                                        psSwapChain->hExtSwapChain);
 
@@ -864,20 +1151,25 @@ static PVRSRV_ERROR DestroyDCSwapChain(PVRSRV_DC_SWAPCHAIN *psSwapChain)
                return eError;
        }
 
-       
+       /* free the resources */
        for(i=0; i<psSwapChain->ui32BufferCount; i++)
        {
                if(psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo)
                {
-                       if (--psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo->ui32RefCount == 0)
-                       {
-                               PVRSRVFreeSyncInfoKM(psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo);
-                       }
+                       PVRSRVKernelSyncInfoDecRef(psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo, IMG_NULL);
                }
        }
 
+#if !defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED)
+       if (psSwapChain->ppsLastSyncInfos)
+       {
+               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_KERNEL_SYNC_INFO *) * psSwapChain->ui32LastNumSyncInfos,
+                                       psSwapChain->ppsLastSyncInfos, IMG_NULL);
+       }
+#endif /* !defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED) */
+
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DC_SWAPCHAIN), psSwapChain, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        return eError;
 }
@@ -901,10 +1193,6 @@ static PVRSRV_ERROR DestroyDCSwapChainRefCallBack(IMG_PVOID pvParam,
                        PVR_DPF((PVR_DBG_ERROR, "DestroyDCSwapChainRefCallBack: swapchain (0x%p) still mapped (ui32MemMapRefCount = %d)",
                                        &psSwapChainRef->psSwapChain->asBuffer[i].sDeviceClassBuffer,
                                        psSwapChainRef->psSwapChain->asBuffer[i].sDeviceClassBuffer.ui32MemMapRefCount));
-#if 0
-                       
-                       return PVRSRV_ERROR_STILL_MAPPED;
-#endif
                }
        }
 
@@ -938,7 +1226,7 @@ static PVRSRV_ERROR PVRSRVCreateDCSwapChainRefKM(PVRSRV_PER_PROCESS_DATA   *psPerP
 {
        PVRSRV_DC_SWAPCHAIN_REF *psSwapChainRef = IMG_NULL;
 
-       
+       /* Allocate swapchain reference structre*/
        if(OSAllocMem( PVRSRV_OS_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_DC_SWAPCHAIN_REF),
                                         (IMG_VOID **)&psSwapChainRef, IMG_NULL,
@@ -949,10 +1237,10 @@ static PVRSRV_ERROR PVRSRVCreateDCSwapChainRefKM(PVRSRV_PER_PROCESS_DATA *psPerP
        }
        OSMemSet (psSwapChainRef, 0, sizeof(PVRSRV_DC_SWAPCHAIN_REF));
 
-       
+       /* Bump refcount */
        psSwapChain->ui32RefCount++;
 
-       
+       /* Create reference resource */
        psSwapChainRef->psSwapChain = psSwapChain;
        psSwapChainRef->hResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                                                  RESMAN_TYPE_DISPLAYCLASS_SWAPCHAIN_REF,
@@ -1012,11 +1300,11 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA *psPerProc,
 
        if( ui32Flags & PVRSRV_CREATE_SWAPCHAIN_QUERY )
        {
-               
+               /* Query - use pui32SwapChainID as input */
                psSwapChain = PVRSRVFindSharedDCSwapChainKM(psDCInfo, *pui32SwapChainID );
                if( psSwapChain  ) 
                {       
-                                          
+                       /* Create new reference */                 
                        eError = PVRSRVCreateDCSwapChainRefKM(psPerProc, 
                                                                                                  psSwapChain, 
                                                                                                  &psSwapChainRef);
@@ -1033,7 +1321,7 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA   *psPerProc,
                return PVRSRV_ERROR_FLIP_CHAIN_EXISTS;          
        }
 
-       
+       /* Allocate swapchain control structure for srvkm */
        if(OSAllocMem( PVRSRV_OS_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_DC_SWAPCHAIN),
                                         (IMG_VOID **)&psSwapChain, IMG_NULL,
@@ -1045,7 +1333,7 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA   *psPerProc,
        }
        OSMemSet (psSwapChain, 0, sizeof(PVRSRV_DC_SWAPCHAIN));
 
-       
+       /* Create a command queue for the swapchain     */
        eError = PVRSRVCreateCommandQueueKM(1024, &psQueue);
        if(eError != PVRSRV_OK)
        {
@@ -1053,10 +1341,10 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA *psPerProc,
                goto ErrorExit;
        }
 
-       
+       /* store the Queue */
        psSwapChain->psQueue = psQueue;
 
-       
+       /* Create a Sync Object for each surface in the swapchain */
        for(i=0; i<ui32BufferCount; i++)
        {
                eError = PVRSRVAllocSyncInfoKM(IMG_NULL,
@@ -1068,18 +1356,16 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA *psPerProc,
                        goto ErrorExit;
                }
 
-               psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo->ui32RefCount++;
-
-               
+               /* setup common device class info */
                psSwapChain->asBuffer[i].sDeviceClassBuffer.pfnGetBufferAddr = psDCInfo->psFuncTable->pfnGetBufferAddr;
                psSwapChain->asBuffer[i].sDeviceClassBuffer.hDevMemContext = psDCInfo->hDevMemContext;
                psSwapChain->asBuffer[i].sDeviceClassBuffer.hExtDevice = psDCInfo->hExtDevice;
 
-               
+               /* save off useful ptrs */
                psSwapChain->asBuffer[i].psDCInfo = psDCInfo;
                psSwapChain->asBuffer[i].psSwapChain = psSwapChain;
 
-               
+               /* syncinfos must be passed as array of syncdata ptrs to the 3rd party driver */
                apsSyncData[i] = (PVRSRV_SYNC_DATA*)psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo->psSyncDataMemInfoKM->pvLinAddrKM;
        }
 
@@ -1108,7 +1394,7 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA   *psPerProc,
        psSwapChain->ui32MinSwapInterval = sDisplayInfo.ui32MinSwapInterval;
        psSwapChain->ui32MaxSwapInterval = sDisplayInfo.ui32MaxSwapInterval;
 
-       
+       /* call into the display device driver to create a swapchain */
        eError =  psDCInfo->psFuncTable->pfnCreateDCSwapChain(psDCInfo->hExtDevice,
                                                                                                                ui32Flags,
                                                                                                                psDstSurfAttrib,
@@ -1125,7 +1411,7 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA   *psPerProc,
                goto ErrorExit;
        }
 
-                          
+       /* Create new reference */                 
        eError = PVRSRVCreateDCSwapChainRefKM(psPerProc, 
                                                                                  psSwapChain, 
                                                                                  &psSwapChainRef);
@@ -1139,7 +1425,7 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA   *psPerProc,
        psSwapChain->ui32RefCount = 1;
        psSwapChain->ui32Flags = ui32Flags;
 
-       
+       /* Save pointer in DC structure if ti's shared struct */
        if( ui32Flags & PVRSRV_CREATE_SWAPCHAIN_SHARED )
        {
                if(! psDCInfo->psDCSwapChainShared ) 
@@ -1154,10 +1440,10 @@ PVRSRV_ERROR PVRSRVCreateDCSwapChainKM (PVRSRV_PER_PROCESS_DATA *psPerProc,
                }
        }
 
-       
+       /* We create swapchain - pui32SwapChainID is output */
        *pui32SwapChainID = psSwapChain->ui32SwapChainID;
 
-       
+       /* return the swapchain reference handle */
        *phSwapChainRef= (IMG_HANDLE)psSwapChainRef;
 
        return eError;
@@ -1168,10 +1454,7 @@ ErrorExit:
        {
                if(psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo)
                {
-                       if (--psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo->ui32RefCount == 0)
-                       {
-                               PVRSRVFreeSyncInfoKM(psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo);
-                       }
+                       PVRSRVKernelSyncInfoDecRef(psSwapChain->asBuffer[i].sDeviceClassBuffer.psKernelSyncInfo, IMG_NULL);
                }
        }
 
@@ -1183,7 +1466,7 @@ ErrorExit:
        if(psSwapChain)
        {
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DC_SWAPCHAIN), psSwapChain, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
        }
 
        return eError;
@@ -1288,7 +1571,8 @@ IMG_EXPORT
 PVRSRV_ERROR PVRSRVGetDCBuffersKM(IMG_HANDLE   hDeviceKM,
                                                                  IMG_HANDLE    hSwapChainRef,
                                                                  IMG_UINT32    *pui32BufferCount,
-                                                                 IMG_HANDLE    *phBuffer)
+                                                                 IMG_HANDLE    *phBuffer,
+                                                                 IMG_SYS_PHYADDR *psPhyAddr)
 {
        PVRSRV_DISPLAYCLASS_INFO *psDCInfo;
        PVRSRV_DC_SWAPCHAIN *psSwapChain;
@@ -1296,7 +1580,7 @@ PVRSRV_ERROR PVRSRVGetDCBuffersKM(IMG_HANDLE      hDeviceKM,
        PVRSRV_ERROR eError;
        IMG_UINT32 i;
 
-       if(!hDeviceKM || !hSwapChainRef || !phBuffer)
+       if(!hDeviceKM || !hSwapChainRef || !phBuffer || !psPhyAddr)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVGetDCBuffersKM: Invalid parameters"));
                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -1305,7 +1589,7 @@ PVRSRV_ERROR PVRSRVGetDCBuffersKM(IMG_HANDLE      hDeviceKM,
        psDCInfo = DCDeviceHandleToDCInfo(hDeviceKM);
        psSwapChain = ((PVRSRV_DC_SWAPCHAIN_REF*)hSwapChainRef)->psSwapChain;
 
-       
+       /* call into the display device driver to get info */
        eError = psDCInfo->psFuncTable->pfnGetDCBuffers(psDCInfo->hExtDevice,
                                                                                                        psSwapChain->hExtSwapChain,
                                                                                                        pui32BufferCount,
@@ -1313,15 +1597,42 @@ PVRSRV_ERROR PVRSRVGetDCBuffersKM(IMG_HANDLE    hDeviceKM,
 
        PVR_ASSERT(*pui32BufferCount <= PVRSRV_MAX_DC_SWAPCHAIN_BUFFERS);
 
-       
-
-
+       /*
+               populate the srvkm's buffer structure with the 3rd party buffer handles
+               and return the services buffer handles
+       */
        for(i=0; i<*pui32BufferCount; i++)
        {
                psSwapChain->asBuffer[i].sDeviceClassBuffer.hExtBuffer = ahExtBuffer[i];
                phBuffer[i] = (IMG_HANDLE)&psSwapChain->asBuffer[i];
        }
 
+#if defined(SUPPORT_GET_DC_BUFFERS_SYS_PHYADDRS)
+       for(i = 0; i < *pui32BufferCount; i++)
+       {
+               IMG_UINT32 ui32ByteSize, ui32TilingStride;
+               IMG_SYS_PHYADDR *pPhyAddr;
+               IMG_BOOL bIsContiguous;
+               IMG_HANDLE hOSMapInfo;
+               IMG_VOID *pvVAddr;
+
+               eError = psDCInfo->psFuncTable->pfnGetBufferAddr(psDCInfo->hExtDevice,
+                                                                                                                ahExtBuffer[i],
+                                                                                                                &pPhyAddr,
+                                                                                                                &ui32ByteSize,
+                                                                                                                &pvVAddr,
+                                                                                                                &hOSMapInfo,
+                                                                                                                &bIsContiguous,
+                                                                                                                &ui32TilingStride);
+               if(eError != PVRSRV_OK)
+               {
+                       break;
+               }
+
+               psPhyAddr[i] = *pPhyAddr;
+       }
+#endif /* defined(SUPPORT_GET_DC_BUFFERS_SYS_PHYADDRS) */
+
        return eError;
 }
 
@@ -1356,7 +1667,7 @@ PVRSRV_ERROR PVRSRVSwapToDCBufferKM(IMG_HANDLE    hDeviceKM,
        psBuffer = (PVRSRV_DC_BUFFER*)hBuffer;
        psDCInfo = DCDeviceHandleToDCInfo(hDeviceKM);
 
-       
+       /* Validate swap interval against limits */
        if(ui32SwapInterval < psBuffer->psSwapChain->ui32MinSwapInterval ||
                ui32SwapInterval > psBuffer->psSwapChain->ui32MaxSwapInterval)
        {
@@ -1380,25 +1691,19 @@ PVRSRV_ERROR PVRSRVSwapToDCBufferKM(IMG_HANDLE  hDeviceKM,
 
 #endif
 
-       
+       /* get the queue from the buffer structure */
        psQueue = psBuffer->psSwapChain->psQueue;
 
-       
+       /* specify the syncs */
        apsSrcSync[0] = psBuffer->sDeviceClassBuffer.psKernelSyncInfo;
-       
-
-
        if(bAddReferenceToLast && psBuffer->psSwapChain->psLastFlipBuffer &&
                psBuffer != psBuffer->psSwapChain->psLastFlipBuffer)
        {
                apsSrcSync[1] = psBuffer->psSwapChain->psLastFlipBuffer->sDeviceClassBuffer.psKernelSyncInfo;
-               
-
-
                ui32NumSrcSyncs++;
        }
 
-       
+       /* insert the command (header) */
        eError = PVRSRVInsertCommandKM (psQueue,
                                                                        &psCommand,
                                                                        psDCInfo->ui32DeviceID,
@@ -1407,52 +1712,78 @@ PVRSRV_ERROR PVRSRVSwapToDCBufferKM(IMG_HANDLE  hDeviceKM,
                                                                        IMG_NULL,
                                                                        ui32NumSrcSyncs,
                                                                        apsSrcSync,
-                                                                       sizeof(DISPLAYCLASS_FLIP_COMMAND) + (sizeof(IMG_RECT) * ui32ClipRectCount));
+                                                                       sizeof(DISPLAYCLASS_FLIP_COMMAND) + (sizeof(IMG_RECT) * ui32ClipRectCount),
+                                                                       IMG_NULL,
+                                                                       IMG_NULL);
        if(eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBufferKM: Failed to get space in queue"));
                goto Exit;
        }
 
-       
+       /*  setup the flip command */
        psFlipCmd = (DISPLAYCLASS_FLIP_COMMAND*)psCommand->pvData;
 
-       
+       /* Ext Device Handle */
        psFlipCmd->hExtDevice = psDCInfo->hExtDevice;
 
-       
+       /* Ext SwapChain Handle */
        psFlipCmd->hExtSwapChain = psBuffer->psSwapChain->hExtSwapChain;
 
-       
+       /* Ext Buffer Handle (Buffer to Flip to) */
        psFlipCmd->hExtBuffer = psBuffer->sDeviceClassBuffer.hExtBuffer;
 
-       
+       /* private tag */
        psFlipCmd->hPrivateTag = hPrivateTag;
 
-       
+       /* setup the clip rects */
        psFlipCmd->ui32ClipRectCount = ui32ClipRectCount;
-       
-       psFlipCmd->psClipRect = (IMG_RECT*)((IMG_UINT8*)psFlipCmd + sizeof(DISPLAYCLASS_FLIP_COMMAND)); 
-       
+       /* cliprect memory appends the command structure */
+       psFlipCmd->psClipRect = (IMG_RECT*)((IMG_UINT8*)psFlipCmd + sizeof(DISPLAYCLASS_FLIP_COMMAND)); // PRQA S 3305
+       /* copy the clip rects */
        for(i=0; i<ui32ClipRectCount; i++)
        {
                psFlipCmd->psClipRect[i] = psClipRect[i];
        }
 
-       
+       /* number of vsyncs between successive flips */
        psFlipCmd->ui32SwapInterval = ui32SwapInterval;
 
-       
-       eError = PVRSRVSubmitCommandKM (psQueue, psCommand);
-       if (eError != PVRSRV_OK)
-       {
-               PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBufferKM: Failed to submit command"));
-               goto Exit;
+       SysAcquireData(&psSysData);
+
+       /* Because we might be composing just software surfaces, without
+        * any SGX renders since the last frame, we won't necessarily
+        * have cleaned/flushed the CPU caches before the buffers need
+        * to be displayed.
+        *
+        * Doing so now is safe because InsertCommand bumped ROP2 on the
+        * affected buffers (preventing more SW renders starting) but the
+        * display won't start to process the buffers until SubmitCommand.
+        */
+       {
+               if(psSysData->ePendingCacheOpType == PVRSRV_MISC_INFO_CPUCACHEOP_FLUSH)
+               {
+                       OSFlushCPUCacheKM();
+               }
+               else if(psSysData->ePendingCacheOpType == PVRSRV_MISC_INFO_CPUCACHEOP_CLEAN)
+               {
+                       OSCleanCPUCacheKM();
+               }
+
+               psSysData->ePendingCacheOpType = PVRSRV_MISC_INFO_CPUCACHEOP_NONE;
        }
 
-       
+       /* submit the command */
+       eError = PVRSRVSubmitCommandKM (psQueue, psCommand);
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBufferKM: Failed to submit command"));
+               goto Exit;
+       }
 
-       SysAcquireData(&psSysData);
+       /*
+               Schedule an MISR to process it
+       */
     eError = OSScheduleMISR(psSysData);
 
        if (eError != PVRSRV_OK)
@@ -1461,7 +1792,7 @@ PVRSRV_ERROR PVRSRVSwapToDCBufferKM(IMG_HANDLE    hDeviceKM,
                goto Exit;
        }
 
-       
+       /* update the last flip buffer */
        psBuffer->psSwapChain->psLastFlipBuffer = psBuffer;
 
 Exit:
@@ -1474,6 +1805,288 @@ Exit:
        return eError;
 }
 
+typedef struct _CALLBACK_DATA_
+{
+       IMG_PVOID       pvPrivData;
+       IMG_UINT32      ui32PrivDataLength;
+       IMG_PVOID       ppvMemInfos;
+       IMG_UINT32      ui32NumMemInfos;
+} CALLBACK_DATA;
+
+static IMG_VOID FreePrivateData(IMG_HANDLE hCallbackData)
+{
+       CALLBACK_DATA *psCallbackData = hCallbackData;
+
+       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, psCallbackData->ui32PrivDataLength,
+                         psCallbackData->pvPrivData, IMG_NULL);
+       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                         sizeof(IMG_VOID *) * psCallbackData->ui32NumMemInfos,
+                         psCallbackData->ppvMemInfos, IMG_NULL);
+       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(CALLBACK_DATA), hCallbackData, IMG_NULL);
+}
+
+IMG_EXPORT
+PVRSRV_ERROR PVRSRVSwapToDCBuffer2KM(IMG_HANDLE        hDeviceKM,
+                                                                        IMG_HANDLE     hSwapChain,
+                                                                        IMG_UINT32     ui32SwapInterval,
+                                                                        PVRSRV_KERNEL_MEM_INFO **ppsMemInfos,
+                                                                        PVRSRV_KERNEL_SYNC_INFO **ppsSyncInfos,
+                                                                        IMG_UINT32     ui32NumMemSyncInfos,
+                                                                        IMG_PVOID      pvPrivData,
+                                                                        IMG_UINT32     ui32PrivDataLength)
+{
+       PVRSRV_KERNEL_SYNC_INFO **ppsCompiledSyncInfos;
+       IMG_UINT32 i, ui32NumCompiledSyncInfos;
+       DISPLAYCLASS_FLIP_COMMAND2 *psFlipCmd;
+       PVRSRV_DISPLAYCLASS_INFO *psDCInfo;
+       PVRSRV_DC_SWAPCHAIN *psSwapChain;
+       PVRSRV_ERROR eError = PVRSRV_OK;
+       CALLBACK_DATA *psCallbackData;
+       PVRSRV_QUEUE_INFO *psQueue;
+       PVRSRV_COMMAND *psCommand;
+       IMG_PVOID *ppvMemInfos;
+       SYS_DATA *psSysData;
+
+       if(!hDeviceKM || !hSwapChain || !ppsMemInfos || !ppsSyncInfos || ui32NumMemSyncInfos < 1)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2KM: Invalid parameters"));
+               return PVRSRV_ERROR_INVALID_PARAMS;
+       }
+
+       psSwapChain = ((PVRSRV_DC_SWAPCHAIN_REF*)hSwapChain)->psSwapChain;
+       psDCInfo = DCDeviceHandleToDCInfo(hDeviceKM);
+
+       /* Validate swap interval against limits */
+       if(ui32SwapInterval < psSwapChain->ui32MinSwapInterval ||
+          ui32SwapInterval > psSwapChain->ui32MaxSwapInterval)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2KM: Invalid swap interval. Requested %u, Allowed range %u-%u",
+                                ui32SwapInterval, psSwapChain->ui32MinSwapInterval, psSwapChain->ui32MaxSwapInterval));
+               return PVRSRV_ERROR_INVALID_SWAPINTERVAL;
+       }
+
+       eError = OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                         sizeof(CALLBACK_DATA),
+                                         (IMG_VOID **)&psCallbackData, IMG_NULL,
+                                         "PVRSRVSwapToDCBuffer2KM callback data");
+       if (eError != PVRSRV_OK)
+       {
+               return eError;
+       }
+
+       psCallbackData->pvPrivData = pvPrivData;
+       psCallbackData->ui32PrivDataLength = ui32PrivDataLength;
+
+       if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                 sizeof(IMG_VOID *) * ui32NumMemSyncInfos,
+                                 (IMG_VOID **)&ppvMemInfos, IMG_NULL,
+                                 "Swap Command Meminfos") != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2KM: Failed to allocate space for meminfo list"));
+               psCallbackData->ppvMemInfos = IMG_NULL;
+               goto Exit;
+       }
+
+       for(i = 0; i < ui32NumMemSyncInfos; i++)
+       {
+               ppvMemInfos[i] = ppsMemInfos[i];
+       }
+
+       psCallbackData->ppvMemInfos = ppvMemInfos;
+       psCallbackData->ui32NumMemInfos = ui32NumMemSyncInfos;
+
+       /* get the queue from the buffer structure */
+       psQueue = psSwapChain->psQueue;
+
+#if !defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED)
+       if(psSwapChain->ppsLastSyncInfos)
+       {
+               IMG_UINT32 ui32NumUniqueSyncInfos = psSwapChain->ui32LastNumSyncInfos;
+               IMG_UINT32 j;
+
+               for(j = 0; j < psSwapChain->ui32LastNumSyncInfos; j++)
+               {
+                       for(i = 0; i < ui32NumMemSyncInfos; i++)
+                       {
+                               if(psSwapChain->ppsLastSyncInfos[j] == ppsSyncInfos[i])
+                               {
+                                       psSwapChain->ppsLastSyncInfos[j] = IMG_NULL;
+                                       ui32NumUniqueSyncInfos--;
+                               }
+                       }
+               }
+
+               ui32NumCompiledSyncInfos = ui32NumMemSyncInfos + ui32NumUniqueSyncInfos;
+
+               if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                         sizeof(PVRSRV_KERNEL_SYNC_INFO *) * ui32NumCompiledSyncInfos,
+                                         (IMG_VOID **)&ppsCompiledSyncInfos, IMG_NULL,
+                                         "Compiled syncinfos") != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2KM: Failed to allocate space for meminfo list"));
+                       goto Exit;
+               }
+                               
+               OSMemCopy(ppsCompiledSyncInfos, ppsSyncInfos, sizeof(PVRSRV_KERNEL_SYNC_INFO *) * ui32NumMemSyncInfos);
+               for(j = 0, i = ui32NumMemSyncInfos; j < psSwapChain->ui32LastNumSyncInfos; j++)
+               {
+                       if(psSwapChain->ppsLastSyncInfos[j])
+                       {
+                               ppsCompiledSyncInfos[i] = psSwapChain->ppsLastSyncInfos[j];
+                               i++;
+                       }
+               }
+       }
+       else
+#endif /* !defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED) */
+       {
+               ppsCompiledSyncInfos = ppsSyncInfos;
+               ui32NumCompiledSyncInfos = ui32NumMemSyncInfos;
+       }
+
+       /* insert the command (header) */
+       eError = PVRSRVInsertCommandKM (psQueue,
+                                                                       &psCommand,
+                                                                       psDCInfo->ui32DeviceID,
+                                                                       DC_FLIP_COMMAND,
+                                                                       0,
+                                                                       IMG_NULL,
+                                                                       ui32NumCompiledSyncInfos,
+                                                                       ppsCompiledSyncInfos,
+                                                                       sizeof(DISPLAYCLASS_FLIP_COMMAND2),
+                                                                       FreePrivateData,
+                                                                       psCallbackData);
+
+       if (ppsCompiledSyncInfos != ppsSyncInfos)
+       {
+               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                         sizeof(PVRSRV_KERNEL_SYNC_INFO *) * ui32NumCompiledSyncInfos,
+                         (IMG_VOID *)ppsCompiledSyncInfos,
+                         IMG_NULL);
+       }
+       if(eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2KM: Failed to get space in queue"));
+               goto Exit;
+       }
+
+       /*  setup the flip command */
+       psFlipCmd = (DISPLAYCLASS_FLIP_COMMAND2*)psCommand->pvData;
+
+       /* Ext Device Handle */
+       psFlipCmd->hExtDevice = psDCInfo->hExtDevice;
+
+       /* Ext SwapChain Handle */
+       psFlipCmd->hExtSwapChain = psSwapChain->hExtSwapChain;
+
+       /* number of vsyncs between successive flips */
+       psFlipCmd->ui32SwapInterval = ui32SwapInterval;
+
+       /* Opaque private data, if supplied */
+       psFlipCmd->pvPrivData = pvPrivData;
+       psFlipCmd->ui32PrivDataLength = ui32PrivDataLength;
+
+       psFlipCmd->ppsMemInfos = (PDC_MEM_INFO *)ppvMemInfos;
+       psFlipCmd->ui32NumMemInfos = ui32NumMemSyncInfos;
+
+       /* Even though this is "unused", we have to initialize it,
+        * as the display controller might NULL-test it.
+        */
+       psFlipCmd->hUnused = IMG_NULL;
+
+       SysAcquireData(&psSysData);
+
+       /* Because we might be composing just software surfaces, without
+        * any SGX renders since the last frame, we won't necessarily
+        * have cleaned/flushed the CPU caches before the buffers need
+        * to be displayed.
+        *
+        * Doing so now is safe because InsertCommand bumped ROP2 on the
+        * affected buffers (preventing more SW renders starting) but the
+        * display won't start to process the buffers until SubmitCommand.
+        */
+       {
+               if(psSysData->ePendingCacheOpType == PVRSRV_MISC_INFO_CPUCACHEOP_FLUSH)
+               {
+                       OSFlushCPUCacheKM();
+               }
+               else if(psSysData->ePendingCacheOpType == PVRSRV_MISC_INFO_CPUCACHEOP_CLEAN)
+               {
+                       OSCleanCPUCacheKM();
+               }
+
+               psSysData->ePendingCacheOpType = PVRSRV_MISC_INFO_CPUCACHEOP_NONE;
+       }
+
+       /* submit the command */
+       eError = PVRSRVSubmitCommandKM (psQueue, psCommand);
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2KM: Failed to submit command"));
+               goto Exit;
+       }
+
+       /* The command has been submitted and so psCallbackData will be freed by the callback */
+       psCallbackData = IMG_NULL;
+
+       /*
+               Schedule an MISR to process it
+       */
+       eError = OSScheduleMISR(psSysData);
+
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2KM: Failed to schedule MISR"));
+               goto Exit;
+       }
+
+#if !defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED)
+       /* Reallocate the syncinfo list if it was too small */
+       if (psSwapChain->ui32LastNumSyncInfos < ui32NumMemSyncInfos)
+       {
+               if (psSwapChain->ppsLastSyncInfos)
+               {
+                       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_KERNEL_SYNC_INFO *) * psSwapChain->ui32LastNumSyncInfos,
+                                               psSwapChain->ppsLastSyncInfos, IMG_NULL);
+               }
+
+               if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                         sizeof(PVRSRV_KERNEL_SYNC_INFO *) * ui32NumMemSyncInfos,
+                                         (IMG_VOID **)&psSwapChain->ppsLastSyncInfos, IMG_NULL,
+                                         "Last syncinfos") != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCBuffer2KM: Failed to allocate space for meminfo list"));
+                       goto Exit;
+               }
+       }
+
+       psSwapChain->ui32LastNumSyncInfos = ui32NumMemSyncInfos;
+
+       for(i = 0; i < ui32NumMemSyncInfos; i++)
+       {
+               psSwapChain->ppsLastSyncInfos[i] = ppsSyncInfos[i];
+       }
+#endif /* !defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED) */
+
+Exit:
+       if (psCallbackData)
+       {
+               if(psCallbackData->ppvMemInfos)
+               {
+                       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                         sizeof(IMG_VOID *) * psCallbackData->ui32NumMemInfos,
+                                         psCallbackData->ppvMemInfos, IMG_NULL);
+               }
+               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(CALLBACK_DATA), psCallbackData, IMG_NULL);
+       }
+       if(eError == PVRSRV_ERROR_CANNOT_GET_QUEUE_SPACE)
+       {
+               eError = PVRSRV_ERROR_RETRY;
+       }
+
+       return eError;
+}
+
 
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVSwapToDCSystemKM(IMG_HANDLE hDeviceKM,
@@ -1502,7 +2115,7 @@ PVRSRV_ERROR PVRSRVSwapToDCSystemKM(IMG_HANDLE    hDeviceKM,
        psSwapChainRef = (PVRSRV_DC_SWAPCHAIN_REF*)hSwapChainRef;
        psSwapChain = psSwapChainRef->psSwapChain;
 
-       
+       /* get the queue from the buffer structure */
        psQueue = psSwapChain->psQueue;
 
 #if defined(SUPPORT_CUSTOM_SWAP_OPERATIONS)
@@ -1520,25 +2133,19 @@ PVRSRV_ERROR PVRSRVSwapToDCSystemKM(IMG_HANDLE  hDeviceKM,
 
 #endif
 
-       
+       /* specify the syncs */
        apsSrcSync[0] = psDCInfo->sSystemBuffer.sDeviceClassBuffer.psKernelSyncInfo;
-       
-
-
        if(bAddReferenceToLast && psSwapChain->psLastFlipBuffer)
        {
-               
+               /* Make sure we don't make a double dependency on the same server */
                if (apsSrcSync[0] != psSwapChain->psLastFlipBuffer->sDeviceClassBuffer.psKernelSyncInfo)
                {
                        apsSrcSync[1] = psSwapChain->psLastFlipBuffer->sDeviceClassBuffer.psKernelSyncInfo;
-                       
-
-
                        ui32NumSrcSyncs++;
                }
        }
 
-       
+       /* insert the command (header) */
        eError = PVRSRVInsertCommandKM (psQueue,
                                                                        &psCommand,
                                                                        psDCInfo->ui32DeviceID,
@@ -1547,34 +2154,36 @@ PVRSRV_ERROR PVRSRVSwapToDCSystemKM(IMG_HANDLE  hDeviceKM,
                                                                        IMG_NULL,
                                                                        ui32NumSrcSyncs,
                                                                        apsSrcSync,
-                                                                       sizeof(DISPLAYCLASS_FLIP_COMMAND));
+                                                                       sizeof(DISPLAYCLASS_FLIP_COMMAND),
+                                                                       IMG_NULL,
+                                                                       IMG_NULL);
        if(eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVSwapToDCSystemKM: Failed to get space in queue"));
                goto Exit;
        }
 
-       
+       /*  setup the flip command */
        psFlipCmd = (DISPLAYCLASS_FLIP_COMMAND*)psCommand->pvData;
 
-       
+       /* Ext Device Handle */
        psFlipCmd->hExtDevice = psDCInfo->hExtDevice;
 
-       
+       /* Ext SwapChain Handle */
        psFlipCmd->hExtSwapChain = psSwapChain->hExtSwapChain;
 
-       
+       /* Ext Buffer Handle (Buffer to Flip to) */
        psFlipCmd->hExtBuffer = psDCInfo->sSystemBuffer.sDeviceClassBuffer.hExtBuffer;
 
-       
+       /* private tag */
        psFlipCmd->hPrivateTag = IMG_NULL;
 
-       
+       /* setup the clip rects */
        psFlipCmd->ui32ClipRectCount = 0;
 
        psFlipCmd->ui32SwapInterval = 1;
 
-       
+       /* submit the command */
        eError = PVRSRVSubmitCommandKM (psQueue, psCommand);
        if (eError != PVRSRV_OK)
        {
@@ -1582,7 +2191,7 @@ PVRSRV_ERROR PVRSRVSwapToDCSystemKM(IMG_HANDLE    hDeviceKM,
                goto Exit;
        }
 
-       
+       /* Schedule an MISR to process it */
        SysAcquireData(&psSysData);
     eError = OSScheduleMISR(psSysData);
 
@@ -1592,7 +2201,7 @@ PVRSRV_ERROR PVRSRVSwapToDCSystemKM(IMG_HANDLE    hDeviceKM,
                goto Exit;
        }
 
-       
+       /* update the last flip buffer */
        psSwapChain->psLastFlipBuffer = &psDCInfo->sSystemBuffer;
 
        eError = PVRSRV_OK;
@@ -1608,6 +2217,26 @@ Exit:
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRegisterSystemISRHandler
+
+ @Description
+
+ registers an external ISR to be called of the back of a system ISR
+
+ @Input           ppfnISRHandler               : ISR pointer
+
+ @Input           hISRHandlerData              : Callback data
+
+ @Input           ui32ISRSourceMask    : ISR Mask
+
+ @Input           ui32DeviceID                 : unique device key
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 static
 PVRSRV_ERROR PVRSRVRegisterSystemISRHandler (PFN_ISR_HANDLER   pfnISRHandler,
                                                                                         IMG_VOID                       *pvISRHandlerData,
@@ -1621,7 +2250,7 @@ PVRSRV_ERROR PVRSRVRegisterSystemISRHandler (PFN_ISR_HANDLER      pfnISRHandler,
 
        SysAcquireData(&psSysData);
 
-       
+       /* Find Dev Node (just using the device id, ignore the class) */
        psDevNode = (PVRSRV_DEVICE_NODE*)
                                List_PVRSRV_DEVICE_NODE_Any_va(psSysData->psDeviceNodeList,
                                                                                                &MatchDeviceKM_AnyVaCb,
@@ -1635,15 +2264,29 @@ PVRSRV_ERROR PVRSRVRegisterSystemISRHandler (PFN_ISR_HANDLER    pfnISRHandler,
                return PVRSRV_ERROR_NO_DEVICENODE_FOUND;
        }
 
-       
+       /* set up data before enabling the ISR */
        psDevNode->pvISRData = (IMG_VOID*) pvISRHandlerData;
 
-       
+       /* enable the ISR */
        psDevNode->pfnDeviceISR = pfnISRHandler;
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSetDCState_ForEachVaCb
+
+ @Description
+
+ If the device node is a display, calls its set state function.
+
+ @Input        psDeviceNode    - the device node
+               va                              - variable argument list with:
+                               ui32State       - the state to be set.
+
+******************************************************************************/
 static
 IMG_VOID PVRSRVSetDCState_ForEachVaCb(PVRSRV_DEVICE_NODE *psDeviceNode, va_list va)
 {
@@ -1662,8 +2305,22 @@ IMG_VOID PVRSRVSetDCState_ForEachVaCb(PVRSRV_DEVICE_NODE *psDeviceNode, va_list
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSetDCState
+
+ @Description
+
+ Calls the display driver(s) to put them into the specified state.
+
+ @Input           ui32State: new DC state - one of DC_STATE_*
+
+******************************************************************************/
 IMG_VOID IMG_CALLCONV PVRSRVSetDCState(IMG_UINT32 ui32State)
 {
+/*     PVRSRV_DISPLAYCLASS_INFO        *psDCInfo;
+       PVRSRV_DEVICE_NODE                      *psDeviceNode; */
        SYS_DATA                                        *psSysData;
 
        SysAcquireData(&psSysData);
@@ -1673,7 +2330,50 @@ IMG_VOID IMG_CALLCONV PVRSRVSetDCState(IMG_UINT32 ui32State)
                                                                                ui32State);
 }
 
+static PVRSRV_ERROR
+PVRSRVDCMemInfoGetCpuVAddr(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo,
+                                                  IMG_CPU_VIRTADDR *pVAddr)
+{
+       *pVAddr = psKernelMemInfo->pvLinAddrKM;
+       return PVRSRV_OK;
+}
 
+static PVRSRV_ERROR
+PVRSRVDCMemInfoGetCpuPAddr(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo,
+                                                  IMG_SIZE_T uByteOffset, IMG_CPU_PHYADDR *pPAddr)
+{
+       *pPAddr = OSMemHandleToCpuPAddr(psKernelMemInfo->sMemBlk.hOSMemHandle, uByteOffset);
+       return PVRSRV_OK;
+}
+
+static PVRSRV_ERROR
+PVRSRVDCMemInfoGetByteSize(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo,
+                                                  IMG_SIZE_T *uByteSize)
+{
+       *uByteSize = psKernelMemInfo->uAllocSize;
+       return PVRSRV_OK;
+}
+
+static IMG_BOOL
+PVRSRVDCMemInfoIsPhysContig(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       return OSMemHandleIsPhysContig(psKernelMemInfo->sMemBlk.hOSMemHandle);
+}
+
+/*!
+******************************************************************************
+
+ @Function     PVRGetDisplayClassJTable
+
+ @Description
+
+ Sets up function table for 3rd party Display Class Device to call through
+
+ @Input           psJTable : pointer to function pointer table memory
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
 IMG_BOOL PVRGetDisplayClassJTable(PVRSRV_DC_DISP2SRV_KMJTABLE *psJTable)
 {
@@ -1693,24 +2393,37 @@ IMG_BOOL PVRGetDisplayClassJTable(PVRSRV_DC_DISP2SRV_KMJTABLE *psJTable)
 #if defined(SUPPORT_CUSTOM_SWAP_OPERATIONS)
        psJTable->pfnPVRSRVFreeCmdCompletePacket = &PVRSRVFreeCommandCompletePacketKM;
 #endif
-
+       psJTable->pfnPVRSRVDCMemInfoGetCpuVAddr = &PVRSRVDCMemInfoGetCpuVAddr;
+       psJTable->pfnPVRSRVDCMemInfoGetCpuPAddr = &PVRSRVDCMemInfoGetCpuPAddr;
+       psJTable->pfnPVRSRVDCMemInfoGetByteSize = &PVRSRVDCMemInfoGetByteSize;
+       psJTable->pfnPVRSRVDCMemInfoIsPhysContig = &PVRSRVDCMemInfoIsPhysContig;
        return IMG_TRUE;
 }
 
 
 
+/******************************************************************************
+
+ @Function     PVRSRVCloseBCDeviceKM
+
+ @Description
+
+ Closes a connection to the Buffer Class device
+
+ @Input           hDeviceKM            : device handle
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
-PVRSRV_ERROR PVRSRVCloseBCDeviceKM (IMG_HANDLE hDeviceKM,
-                                                                       IMG_BOOL        bResManCallback)
+PVRSRV_ERROR PVRSRVCloseBCDeviceKM (IMG_HANDLE hDeviceKM)
 {
        PVRSRV_ERROR eError;
        PVRSRV_BUFFERCLASS_PERCONTEXT_INFO *psBCPerContextInfo;
 
-       PVR_UNREFERENCED_PARAMETER(bResManCallback);
-
        psBCPerContextInfo = (PVRSRV_BUFFERCLASS_PERCONTEXT_INFO *)hDeviceKM;
 
-       
+       /* Remove the item from the resman list and trigger the callback. */
        eError = ResManFreeResByPtr(psBCPerContextInfo->hResItem, CLEANUP_WITH_POLL);
 
        return eError;
@@ -1731,7 +2444,7 @@ static PVRSRV_ERROR CloseBCDeviceCallBack(IMG_PVOID  pvParam,
        psBCPerContextInfo = (PVRSRV_BUFFERCLASS_PERCONTEXT_INFO *)pvParam;
 
        psBCInfo = psBCPerContextInfo->psBCInfo;
-#if 0
+
        for (i = 0; i < psBCInfo->ui32BufferCount; i++)
        {
                if (psBCInfo->psBuffer[i].sDeviceClassBuffer.ui32MemMapRefCount != 0)
@@ -1743,37 +2456,23 @@ static PVRSRV_ERROR CloseBCDeviceCallBack(IMG_PVOID  pvParam,
                        return PVRSRV_ERROR_STILL_MAPPED;
                }
        }
-#endif
+
        psBCInfo->ui32RefCount--;
        if(psBCInfo->ui32RefCount == 0)
        {
-               for (i = 0; i < psBCInfo->ui32BufferCount; i++)
-               {       
-                       if (psBCInfo->psBuffer[i].sDeviceClassBuffer.ui32MemMapRefCount != 0)
-                       {
-                       PVR_DPF((PVR_DBG_ERROR, "CloseBCDeviceCallBack: buffer %d (0x%p) still mapped (ui32MemMapRefCount = %d)",
-                                       i,
-                                       &psBCInfo->psBuffer[i].sDeviceClassBuffer,
-                                       psBCInfo->psBuffer[i].sDeviceClassBuffer.ui32MemMapRefCount));
-                       return PVRSRV_ERROR_STILL_MAPPED;
-                       }       
-               }
-               
+               /* close the external device */
                psBCInfo->psFuncTable->pfnCloseBCDevice(psBCInfo->ui32DeviceID, psBCInfo->hExtDevice);
 
-               
+               /* free syncinfos */
                for(i=0; i<psBCInfo->ui32BufferCount; i++)
                {
                        if(psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo)
                        {
-                               if (--psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo->ui32RefCount == 0)
-                               {
-                                       PVRSRVFreeSyncInfoKM(psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo);
-                               }
+                               PVRSRVKernelSyncInfoDecRef(psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo, IMG_NULL);
                        }
                }
 
-               
+               /* free buffers */
                if(psBCInfo->psBuffer)
                {
                        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_BC_BUFFER) * psBCInfo->ui32BufferCount, psBCInfo->psBuffer, IMG_NULL);
@@ -1782,12 +2481,31 @@ static PVRSRV_ERROR CloseBCDeviceCallBack(IMG_PVOID  pvParam,
        }
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_BUFFERCLASS_PERCONTEXT_INFO), psBCPerContextInfo, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVOpenBCDeviceKM
+
+ @Description
+
+ Opens a connection to the Buffer Class device, associating the connection
+ with a Device Memory Context for a services managed device
+
+ @Input           psPerProc            : Per-process data
+ @Input           ui32DeviceID         : unique device index
+ @Input           hDevCookie           : devcookie used to derive the Device Memory
+                                                               Context into BC surfaces will be mapped into
+ @Outut           phDeviceKM           : handle to the DC device
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA     *psPerProc,
                                                                   IMG_UINT32                           ui32DeviceID,
@@ -1809,7 +2527,7 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA        *psPerProc,
 
        SysAcquireData(&psSysData);
 
-       
+       /* find the matching devicenode */
        psDeviceNode = (PVRSRV_DEVICE_NODE*)
                        List_PVRSRV_DEVICE_NODE_Any_va(psSysData->psDeviceNodeList,
                                                                                   &MatchDeviceKM_AnyVaCb,
@@ -1823,9 +2541,13 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA       *psPerProc,
        }
        psBCInfo = (PVRSRV_BUFFERCLASS_INFO*)psDeviceNode->pvDevice;
 
-       
-
-
+/*
+FoundDevice:
+*/
+       /*
+               Allocate the per-context BC Info before calling the external device,
+               to make error handling easier.
+       */
        if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                  sizeof(*psBCPerContextInfo),
                                  (IMG_VOID **)&psBCPerContextInfo, IMG_NULL,
@@ -1842,10 +2564,10 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA      *psPerProc,
 
                psDeviceNode = (PVRSRV_DEVICE_NODE *)hDevCookie;
 
-               
+               /* store the device kernel context to map into */
                psBCInfo->hDevMemContext = (IMG_HANDLE)psDeviceNode->sDevMemoryInfo.pBMKernelContext;
 
-               
+               /* open the external device */
                eError = psBCInfo->psFuncTable->pfnOpenBCDevice(ui32DeviceID, &psBCInfo->hExtDevice);
                if(eError != PVRSRV_OK)
                {
@@ -1853,7 +2575,7 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA        *psPerProc,
                        return eError;
                }
 
-               
+               /* get information about the buffers */
                eError = psBCInfo->psFuncTable->pfnGetBCInfo(psBCInfo->hExtDevice, &sBufferInfo);
                if(eError != PVRSRV_OK)
                {
@@ -1861,11 +2583,10 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA      *psPerProc,
                        return eError;
                }
 
-               
+               /* interpret and store info */
                psBCInfo->ui32BufferCount = sBufferInfo.ui32BufferCount;
-               
 
-               
+               /*  allocate BC buffers */
                eError = OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                                          sizeof(PVRSRV_BC_BUFFER) * sBufferInfo.ui32BufferCount,
                                                          (IMG_VOID **)&psBCInfo->psBuffer,
@@ -1882,7 +2603,7 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA        *psPerProc,
 
                for(i=0; i<psBCInfo->ui32BufferCount; i++)
                {
-                       
+                       /* create a syncinfo for the device's system surface */
                        eError = PVRSRVAllocSyncInfoKM(IMG_NULL,
                                                                                psBCInfo->hDevMemContext,
                                                                                &psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo);
@@ -1891,12 +2612,11 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA      *psPerProc,
                                PVR_DPF((PVR_DBG_ERROR,"PVRSRVOpenBCDeviceKM: Failed sync info alloc"));
                                goto ErrorExit;
                        }
-
-                       psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo->ui32RefCount++;
-                       
                        
-
-
+                       /*
+                               get the buffers from the buffer class
+                               drivers by index, passing-in the syncdata objects
+                       */
                        eError = psBCInfo->psFuncTable->pfnGetBCBuffer(psBCInfo->hExtDevice,
                                                                                                                        i,
                                                                                                                        psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo->psSyncData,
@@ -1907,7 +2627,7 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA        *psPerProc,
                                goto ErrorExit;
                        }
 
-                       
+                       /* setup common device class info */
                        psBCInfo->psBuffer[i].sDeviceClassBuffer.pfnGetBufferAddr = psBCInfo->psFuncTable->pfnGetBufferAddr;
                        psBCInfo->psBuffer[i].sDeviceClassBuffer.hDevMemContext = psBCInfo->hDevMemContext;
                        psBCInfo->psBuffer[i].sDeviceClassBuffer.hExtDevice = psBCInfo->hExtDevice;
@@ -1922,26 +2642,23 @@ PVRSRV_ERROR PVRSRVOpenBCDeviceKM (PVRSRV_PER_PROCESS_DATA      *psPerProc,
                                                                                                         0,
                                                                                                         &CloseBCDeviceCallBack);
 
-       
+       /* return a reference to the BCPerContextInfo */
        *phDeviceKM = (IMG_HANDLE)psBCPerContextInfo;
 
        return PVRSRV_OK;
 
 ErrorExit:
 
-       
+       /* free syncinfos */
        for(i=0; i<psBCInfo->ui32BufferCount; i++)
        {
                if(psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo)
                {
-                       if (--psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo->ui32RefCount == 0)
-                       {
-                               PVRSRVFreeSyncInfoKM(psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo);
-                       }
+                       PVRSRVKernelSyncInfoDecRef(psBCInfo->psBuffer[i].sDeviceClassBuffer.psKernelSyncInfo, IMG_NULL);
                }
        }
 
-       
+       /* free buffers */
        if(psBCInfo->psBuffer)
        {
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_BC_BUFFER), psBCInfo->psBuffer, IMG_NULL);
@@ -1954,6 +2671,20 @@ ErrorExit:
 
 
 
+/******************************************************************************
+
+ @Function     PVRSRVGetBCInfoKM
+
+ @Description
+
+ Gets Buffer Class device Info
+
+ @Input                hDeviceKM               : device handle
+ @Output       psBufferInfo
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVGetBCInfoKM (IMG_HANDLE hDeviceKM,
                                                                BUFFER_INFO *psBufferInfo)
@@ -1981,6 +2712,20 @@ PVRSRV_ERROR PVRSRVGetBCInfoKM (IMG_HANDLE hDeviceKM,
 }
 
 
+/******************************************************************************
+
+ @Function     PVRSRVGetBCBufferKM
+
+ @Description
+
+ Gets Buffer Class Buffer Handle
+
+ @Input                hDeviceKM               : device handle
+ @Output       psBufferInfo
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVGetBCBufferKM (IMG_HANDLE hDeviceKM,
                                                                  IMG_UINT32 ui32BufferIndex,
@@ -2010,6 +2755,20 @@ PVRSRV_ERROR PVRSRVGetBCBufferKM (IMG_HANDLE hDeviceKM,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRGetBufferClassJTable
+
+ @Description
+
+ Sets up function table for 3rd party Buffer Class Device to call through
+
+ @Input           psJTable : pointer to function pointer table memory
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
 IMG_BOOL PVRGetBufferClassJTable(PVRSRV_BC_BUFFER2SRV_KMJTABLE *psJTable)
 {
@@ -2022,3 +2781,6 @@ IMG_BOOL PVRGetBufferClassJTable(PVRSRV_BC_BUFFER2SRV_KMJTABLE *psJTable)
        return IMG_TRUE;
 }
 
+/******************************************************************************
+ End of file (deviceclass.c)
+******************************************************************************/
index 9a7bdb3..1cf9f0f 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device ID helpers
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __DEVICEID_H__
 #define __DEVICEID_H__
@@ -33,4 +48,4 @@
 PVRSRV_ERROR AllocateDeviceID(SYS_DATA *psSysData, IMG_UINT32 *pui32DevID);
 PVRSRV_ERROR FreeDeviceID(SYS_DATA *psSysData, IMG_UINT32 ui32DevID);
 
-#endif 
+#endif /* __DEVICEID_H__ */
index a659bba..519eea2 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device addressable memory functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Device addressable memory APIs
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <stddef.h>
 
 #include "pvr_bridge_km.h"
 #include "osfunc.h"
 
-static PVRSRV_ERROR AllocDeviceMem(IMG_HANDLE          hDevCookie,
-                                                                       IMG_HANDLE              hDevMemHeap,
-                                                                       IMG_UINT32              ui32Flags,
-                                                                       IMG_SIZE_T              ui32Size,
-                                                                       IMG_SIZE_T              ui32Alignment,
-                                                                       PVRSRV_KERNEL_MEM_INFO  **ppsMemInfo);
+#if defined(SUPPORT_ION)
+#include "ion.h"
+#include "env_perproc.h"
+#endif
 
+/* local function prototypes */
+static PVRSRV_ERROR AllocDeviceMem(IMG_HANDLE          hDevCookie,
+                                                                  IMG_HANDLE           hDevMemHeap,
+                                                                  IMG_UINT32           ui32Flags,
+                                                                  IMG_SIZE_T           ui32Size,
+                                                                  IMG_SIZE_T           ui32Alignment,
+                                                                  IMG_PVOID            pvPrivData,
+                                                                  IMG_UINT32           ui32PrivDataLength,
+                                                                  IMG_UINT32           ui32ChunkSize,
+                                                                  IMG_UINT32           ui32NumVirtChunks,
+                                                                  IMG_UINT32           ui32NumPhysChunks,
+                                                                  IMG_BOOL                     *pabMapChunk,
+                                                                  PVRSRV_KERNEL_MEM_INFO **ppsMemInfo);
+
+/* local structures */
+
+/*
+       structure stored in resman to store references
+       to the SRC and DST meminfo
+*/
 typedef struct _RESMAN_MAP_DEVICE_MEM_DATA_
 {
-       
+       /* the DST meminfo created by the map */
        PVRSRV_KERNEL_MEM_INFO  *psMemInfo;
-       
+       /* SRC meminfo */
        PVRSRV_KERNEL_MEM_INFO  *psSrcMemInfo;
 } RESMAN_MAP_DEVICE_MEM_DATA;
 
+/*
+       map device class resman memory storage structure
+*/
 typedef struct _PVRSRV_DC_MAPINFO_
 {
        PVRSRV_KERNEL_MEM_INFO  *psMemInfo;
@@ -58,6 +95,22 @@ typedef struct _PVRSRV_DC_MAPINFO_
 
 static IMG_UINT32 g_ui32SyncUID = 0;
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVGetDeviceMemHeapsKM
+
+ @Description
+
+ Gets the device shared memory heaps
+
+ @Input           hDevCookie :
+ @Output   phDevMemContext : ptr to handle to memory context
+ @Output   psHeapInfo : ptr to array of heap info
+
+ @Return   PVRSRV_DEVICE_NODE, valid devnode or IMG_NULL
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapsKM(IMG_HANDLE hDevCookie,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -80,22 +133,24 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapsKM(IMG_HANDLE hDevCookie,
 
        psDeviceNode = (PVRSRV_DEVICE_NODE *)hDevCookie;
 
-       
+       /* Setup useful pointers */
        ui32HeapCount = psDeviceNode->sDevMemoryInfo.ui32HeapCount;
        psDeviceMemoryHeap = psDeviceNode->sDevMemoryInfo.psDeviceMemoryHeap;
 
-       
+       /* check we don't exceed the max number of heaps */
        PVR_ASSERT(ui32HeapCount <= PVRSRV_MAX_CLIENT_HEAPS);
 
-       
+       /* retrieve heap information */
        for(i=0; i<ui32HeapCount; i++)
        {
-               
+               /* return information about the heap */
                psHeapInfo[i].ui32HeapID = psDeviceMemoryHeap[i].ui32HeapID;
                psHeapInfo[i].hDevMemHeap = psDeviceMemoryHeap[i].hDevMemHeap;
                psHeapInfo[i].sDevVAddrBase = psDeviceMemoryHeap[i].sDevVAddrBase;
                psHeapInfo[i].ui32HeapByteSize = psDeviceMemoryHeap[i].ui32HeapSize;
                psHeapInfo[i].ui32Attribs = psDeviceMemoryHeap[i].ui32Attribs;
+               /* (XTileStride > 0) denotes a tiled heap */
+               psHeapInfo[i].ui32XTileStride = psDeviceMemoryHeap[i].ui32XTileStride;
        }
 
        for(; i < PVRSRV_MAX_CLIENT_HEAPS; i++)
@@ -107,6 +162,24 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapsKM(IMG_HANDLE hDevCookie,
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVCreateDeviceMemContextKM
+
+ @Description
+
+ Creates a device memory context
+
+ @Input           hDevCookie :
+ @Input           psPerProc : Per-process data
+ @Output   phDevMemContext : ptr to handle to memory context
+ @Output   pui32ClientHeapCount : ptr to heap count
+ @Output   psHeapInfo : ptr to array of heap info
+
+ @Return   PVRSRV_DEVICE_NODE, valid devnode or IMG_NULL
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateDeviceMemContextKM(IMG_HANDLE                                    hDevCookie,
                                                                                                                 PVRSRV_PER_PROCESS_DATA        *psPerProc,
@@ -141,17 +214,20 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateDeviceMemContextKM(IMG_HANDLE                                       hDevCook
 
        psDeviceNode = (PVRSRV_DEVICE_NODE *)hDevCookie;
 
-       
-
+       /*
+               Setup useful pointers
+       */
        ui32HeapCount = psDeviceNode->sDevMemoryInfo.ui32HeapCount;
        psDeviceMemoryHeap = psDeviceNode->sDevMemoryInfo.psDeviceMemoryHeap;
 
-       
-
+       /*
+               check we don't exceed the max number of heaps
+       */
        PVR_ASSERT(ui32HeapCount <= PVRSRV_MAX_CLIENT_HEAPS);
 
-       
-
+       /*
+               Create a memory context for the caller
+       */
        hDevMemContext = BM_CreateContext(psDeviceNode,
                                                                          &sPDDevPAddr,
                                                                          psPerProc,
@@ -162,19 +238,25 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateDeviceMemContextKM(IMG_HANDLE                                       hDevCook
                return PVRSRV_ERROR_OUT_OF_MEMORY;
        }
 
-       
+       /* create the per context heaps */
        for(i=0; i<ui32HeapCount; i++)
        {
                switch(psDeviceMemoryHeap[i].DevMemHeapType)
                {
                        case DEVICE_MEMORY_HEAP_SHARED_EXPORTED:
                        {
-                               
+                               /* return information about the heap */
                                psHeapInfo[ui32ClientHeapCount].ui32HeapID = psDeviceMemoryHeap[i].ui32HeapID;
                                psHeapInfo[ui32ClientHeapCount].hDevMemHeap = psDeviceMemoryHeap[i].hDevMemHeap;
                                psHeapInfo[ui32ClientHeapCount].sDevVAddrBase = psDeviceMemoryHeap[i].sDevVAddrBase;
                                psHeapInfo[ui32ClientHeapCount].ui32HeapByteSize = psDeviceMemoryHeap[i].ui32HeapSize;
                                psHeapInfo[ui32ClientHeapCount].ui32Attribs = psDeviceMemoryHeap[i].ui32Attribs;
+                               #if defined(SUPPORT_MEMORY_TILING)
+                               psHeapInfo[ui32ClientHeapCount].ui32XTileStride = psDeviceMemoryHeap[i].ui32XTileStride;
+                               #else
+                               psHeapInfo[ui32ClientHeapCount].ui32XTileStride = 0;
+                               #endif
+
 #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)
                                pbShared[ui32ClientHeapCount] = IMG_TRUE;
 #endif
@@ -198,12 +280,17 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateDeviceMemContextKM(IMG_HANDLE                                       hDevCook
                                        hDevMemHeap = IMG_NULL;
                                }
 
-                               
+                               /* return information about the heap */
                                psHeapInfo[ui32ClientHeapCount].ui32HeapID = psDeviceMemoryHeap[i].ui32HeapID;
                                psHeapInfo[ui32ClientHeapCount].hDevMemHeap = hDevMemHeap;
                                psHeapInfo[ui32ClientHeapCount].sDevVAddrBase = psDeviceMemoryHeap[i].sDevVAddrBase;
                                psHeapInfo[ui32ClientHeapCount].ui32HeapByteSize = psDeviceMemoryHeap[i].ui32HeapSize;
                                psHeapInfo[ui32ClientHeapCount].ui32Attribs = psDeviceMemoryHeap[i].ui32Attribs;
+                               #if defined(SUPPORT_MEMORY_TILING)
+                               psHeapInfo[ui32ClientHeapCount].ui32XTileStride = psDeviceMemoryHeap[i].ui32XTileStride;
+                               #else
+                               psHeapInfo[ui32ClientHeapCount].ui32XTileStride = 0;
+                               #endif
 #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)
                                pbShared[ui32ClientHeapCount] = IMG_FALSE;
 #endif
@@ -214,7 +301,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateDeviceMemContextKM(IMG_HANDLE                                 hDevCook
                }
        }
 
-       
+       /* return shared_exported and per context heap information to the caller */
        *pui32ClientHeapCount = ui32ClientHeapCount;
        *phDevMemContext = hDevMemContext;
 
@@ -234,6 +321,23 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyDeviceMemContextKM(IMG_HANDLE hDevCookie,
 
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVGetDeviceMemHeapInfoKM
+
+ @Description
+
+ gets heap info
+
+ @Input           hDevCookie :
+ @Input    hDevMemContext : ptr to handle to memory context
+ @Output   pui32ClientHeapCount : ptr to heap count
+ @Output   psHeapInfo : ptr to array of heap info
+
+ @Return
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapInfoKM(IMG_HANDLE                                      hDevCookie,
                                                                                                                 IMG_HANDLE                             hDevMemContext,
@@ -264,28 +368,31 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapInfoKM(IMG_HANDLE                                 hDevCookie
 
        psDeviceNode = (PVRSRV_DEVICE_NODE *)hDevCookie;
 
-       
-
+       /*
+               Setup useful pointers
+       */
        ui32HeapCount = psDeviceNode->sDevMemoryInfo.ui32HeapCount;
        psDeviceMemoryHeap = psDeviceNode->sDevMemoryInfo.psDeviceMemoryHeap;
 
-       
-
+       /*
+               check we don't exceed the max number of heaps
+       */
        PVR_ASSERT(ui32HeapCount <= PVRSRV_MAX_CLIENT_HEAPS);
 
-       
+       /* create the per context heaps */
        for(i=0; i<ui32HeapCount; i++)
        {
                switch(psDeviceMemoryHeap[i].DevMemHeapType)
                {
                        case DEVICE_MEMORY_HEAP_SHARED_EXPORTED:
                        {
-                               
+                               /* return information about the heap */
                                psHeapInfo[ui32ClientHeapCount].ui32HeapID = psDeviceMemoryHeap[i].ui32HeapID;
                                psHeapInfo[ui32ClientHeapCount].hDevMemHeap = psDeviceMemoryHeap[i].hDevMemHeap;
                                psHeapInfo[ui32ClientHeapCount].sDevVAddrBase = psDeviceMemoryHeap[i].sDevVAddrBase;
                                psHeapInfo[ui32ClientHeapCount].ui32HeapByteSize = psDeviceMemoryHeap[i].ui32HeapSize;
                                psHeapInfo[ui32ClientHeapCount].ui32Attribs = psDeviceMemoryHeap[i].ui32Attribs;
+                               psHeapInfo[ui32ClientHeapCount].ui32XTileStride = psDeviceMemoryHeap[i].ui32XTileStride;
 #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)
                                pbShared[ui32ClientHeapCount] = IMG_TRUE;
 #endif
@@ -309,12 +416,13 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapInfoKM(IMG_HANDLE                                 hDevCookie
                                        hDevMemHeap = IMG_NULL;
                                }
 
-                               
+                               /* return information about the heap */
                                psHeapInfo[ui32ClientHeapCount].ui32HeapID = psDeviceMemoryHeap[i].ui32HeapID;
                                psHeapInfo[ui32ClientHeapCount].hDevMemHeap = hDevMemHeap;
                                psHeapInfo[ui32ClientHeapCount].sDevVAddrBase = psDeviceMemoryHeap[i].sDevVAddrBase;
                                psHeapInfo[ui32ClientHeapCount].ui32HeapByteSize = psDeviceMemoryHeap[i].ui32HeapSize;
                                psHeapInfo[ui32ClientHeapCount].ui32Attribs = psDeviceMemoryHeap[i].ui32Attribs;
+                               psHeapInfo[ui32ClientHeapCount].ui32XTileStride = psDeviceMemoryHeap[i].ui32XTileStride;
 #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)
                                pbShared[ui32ClientHeapCount] = IMG_FALSE;
 #endif
@@ -325,23 +433,57 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetDeviceMemHeapInfoKM(IMG_HANDLE                                 hDevCookie
                }
        }
 
-       
+       /* return shared_exported and per context heap information to the caller */
        *pui32ClientHeapCount = ui32ClientHeapCount;
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     AllocDeviceMem
+
+ @Description
+
+ Allocates device memory
+
+ @Input           hDevCookie :
+
+ @Input           hDevMemHeap
+
+ @Input           ui32Flags : Some combination of PVRSRV_MEM_ flags
+
+ @Input           ui32Size :  Number of bytes to allocate
+
+ @Input           ui32Alignment : Alignment of allocation
+
+ @Input    pvPrivData : Opaque private data passed through to allocator
+
+ @Input    ui32PrivDataLength : Length of opaque private data
+
+ @Output   **ppsMemInfo : On success, receives a pointer to the created MEM_INFO structure
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 static PVRSRV_ERROR AllocDeviceMem(IMG_HANDLE          hDevCookie,
-                                                                       IMG_HANDLE              hDevMemHeap,
-                                                                       IMG_UINT32              ui32Flags,
-                                                                       IMG_SIZE_T              ui32Size,
-                                                                       IMG_SIZE_T              ui32Alignment,
-                                                                       PVRSRV_KERNEL_MEM_INFO  **ppsMemInfo)
+                                                                  IMG_HANDLE           hDevMemHeap,
+                                                                  IMG_UINT32           ui32Flags,
+                                                                  IMG_SIZE_T           ui32Size,
+                                                                  IMG_SIZE_T           ui32Alignment,
+                                                                  IMG_PVOID            pvPrivData,
+                                                                  IMG_UINT32           ui32PrivDataLength,
+                                                                  IMG_UINT32           ui32ChunkSize,
+                                                                  IMG_UINT32           ui32NumVirtChunks,
+                                                                  IMG_UINT32           ui32NumPhysChunks,
+                                                                  IMG_BOOL                     *pabMapChunk,
+                                                                  PVRSRV_KERNEL_MEM_INFO **ppsMemInfo)
 {
        PVRSRV_KERNEL_MEM_INFO  *psMemInfo;
        BM_HANDLE               hBuffer;
-       
+       /* Pointer to implementation details within the mem_info */
        PVRSRV_MEMBLK   *psMemBlock;
        IMG_BOOL                bBMError;
 
@@ -362,7 +504,7 @@ static PVRSRV_ERROR AllocDeviceMem(IMG_HANDLE               hDevCookie,
 
        psMemBlock = &(psMemInfo->sMemBlk);
 
-       
+       /* BM supplied Device Virtual Address with physical backing RAM */
        psMemInfo->ui32Flags = ui32Flags | PVRSRV_MEM_RAM_BACKED_ALLOCATION;
 
        bBMError = BM_Alloc (hDevMemHeap,
@@ -370,42 +512,59 @@ static PVRSRV_ERROR AllocDeviceMem(IMG_HANDLE             hDevCookie,
                                                        ui32Size,
                                                        &psMemInfo->ui32Flags,
                                                        IMG_CAST_TO_DEVVADDR_UINT(ui32Alignment),
+                                                       pvPrivData,
+                                                       ui32PrivDataLength,
+                                                       ui32ChunkSize,
+                                                       ui32NumVirtChunks,
+                                                       ui32NumPhysChunks,
+                                                       pabMapChunk,
                                                        &hBuffer);
 
        if (!bBMError)
        {
                PVR_DPF((PVR_DBG_ERROR,"AllocDeviceMem: BM_Alloc Failed"));
                OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(PVRSRV_KERNEL_MEM_INFO), psMemInfo, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
                return PVRSRV_ERROR_OUT_OF_MEMORY;
        }
 
-       
+       /* Fill in "Implementation dependant" section of mem info */
        psMemBlock->sDevVirtAddr = BM_HandleToDevVaddr(hBuffer);
        psMemBlock->hOSMemHandle = BM_HandleToOSMemHandle(hBuffer);
 
-       
+       /* Convert from BM_HANDLE to external IMG_HANDLE */
        psMemBlock->hBuffer = (IMG_HANDLE)hBuffer;
 
-       
+       /* Fill in the public fields of the MEM_INFO structure */
 
        psMemInfo->pvLinAddrKM = BM_HandleToCpuVaddr(hBuffer);
 
        psMemInfo->sDevVAddr = psMemBlock->sDevVirtAddr;
 
-       psMemInfo->uAllocSize = ui32Size;
+       if (ui32Flags & PVRSRV_MEM_SPARSE)
+       {
+               psMemInfo->uAllocSize = ui32ChunkSize * ui32NumVirtChunks;
+       }
+       else
+       {
+               psMemInfo->uAllocSize = ui32Size;
+       }
 
-       
+       /* Clear the Backup buffer pointer as we do not have one at this point. We only allocate this as we are going up/down */
        psMemInfo->pvSysBackupBuffer = IMG_NULL;
 
-       
+       /*
+        * Setup the output.
+        */
        *ppsMemInfo = psMemInfo;
 
-       
+       /*
+        * And I think we're done for now....
+        */
        return (PVRSRV_OK);
 }
 
-static PVRSRV_ERROR FreeDeviceMem2(PVRSRV_KERNEL_MEM_INFO *psMemInfo, IMG_BOOL bFromAllocator)
+static PVRSRV_ERROR FreeDeviceMem2(PVRSRV_KERNEL_MEM_INFO *psMemInfo, PVRSRV_FREE_CALLBACK_ORIGIN eCallbackOrigin)
 {
        BM_HANDLE               hBuffer;
 
@@ -416,23 +575,27 @@ static PVRSRV_ERROR FreeDeviceMem2(PVRSRV_KERNEL_MEM_INFO *psMemInfo, IMG_BOOL b
 
        hBuffer = psMemInfo->sMemBlk.hBuffer;
 
-       
-       if (bFromAllocator)
-               BM_Free(hBuffer, psMemInfo->ui32Flags);
-       else
-               BM_FreeExport(hBuffer, psMemInfo->ui32Flags);
+       switch(eCallbackOrigin)
+       {
+               case PVRSRV_FREE_CALLBACK_ORIGIN_ALLOCATOR:
+                       BM_Free(hBuffer, psMemInfo->ui32Flags);
+                       break;
+               case PVRSRV_FREE_CALLBACK_ORIGIN_IMPORTER:
+                       BM_FreeExport(hBuffer, psMemInfo->ui32Flags);
+                       break;
+               default:
+                       break;
+       }
 
-       
-       if ((psMemInfo->pvSysBackupBuffer) && bFromAllocator)
+       if (psMemInfo->pvSysBackupBuffer &&
+               eCallbackOrigin == PVRSRV_FREE_CALLBACK_ORIGIN_ALLOCATOR)
        {
-               
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, psMemInfo->uAllocSize, psMemInfo->pvSysBackupBuffer, IMG_NULL);
                psMemInfo->pvSysBackupBuffer = IMG_NULL;
        }
 
        if (psMemInfo->ui32RefCount == 0)
                OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(PVRSRV_KERNEL_MEM_INFO), psMemInfo, IMG_NULL);
-       
 
        return(PVRSRV_OK);
 }
@@ -448,23 +611,32 @@ static PVRSRV_ERROR FreeDeviceMem(PVRSRV_KERNEL_MEM_INFO *psMemInfo)
 
        hBuffer = psMemInfo->sMemBlk.hBuffer;
 
-       
        BM_Free(hBuffer, psMemInfo->ui32Flags);
 
        if(psMemInfo->pvSysBackupBuffer)
        {
-               
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, psMemInfo->uAllocSize, psMemInfo->pvSysBackupBuffer, IMG_NULL);
                psMemInfo->pvSysBackupBuffer = IMG_NULL;
        }
 
        OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(PVRSRV_KERNEL_MEM_INFO), psMemInfo, IMG_NULL);
-       
 
        return(PVRSRV_OK);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVAllocSyncInfoKM
+
+ @Description
+
+ Allocates a sync info
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocSyncInfoKM(IMG_HANDLE                                     hDevCookie,
                                                                                                IMG_HANDLE                                      hDevMemContext,
@@ -487,35 +659,47 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocSyncInfoKM(IMG_HANDLE                                        hDevCookie,
                return PVRSRV_ERROR_OUT_OF_MEMORY;
        }
 
-       psKernelSyncInfo->ui32RefCount = 0;
-
+       eError = OSAtomicAlloc(&psKernelSyncInfo->pvRefCount);
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVAllocSyncInfoKM: Failed to allocate atomic"));
+               OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(PVRSRV_KERNEL_SYNC_INFO), psKernelSyncInfo, IMG_NULL);
+               return PVRSRV_ERROR_OUT_OF_MEMORY;
+       }
        
+
+       /* Get the devnode from the devheap */
        pBMContext = (BM_CONTEXT*)hDevMemContext;
        psDevMemoryInfo = &pBMContext->psDeviceNode->sDevMemoryInfo;
 
-       
+       /* and choose a heap for the syncinfo */
        hSyncDevMemHeap = psDevMemoryInfo->psDeviceMemoryHeap[psDevMemoryInfo->ui32SyncHeapID].hDevMemHeap;
 
-       
-
-
+       /*
+               Cache consistent flag would be unnecessary if the heap attributes were
+               changed to specify it.
+       */
        eError = AllocDeviceMem(hDevCookie,
                                                        hSyncDevMemHeap,
                                                        PVRSRV_MEM_CACHE_CONSISTENT,
                                                        sizeof(PVRSRV_SYNC_DATA),
                                                        sizeof(IMG_UINT32),
+                                                       IMG_NULL,
+                                                       0,
+                                                       0, 0, 0, IMG_NULL, /* Sparse mapping args, not required */
                                                        &psKernelSyncInfo->psSyncDataMemInfoKM);
 
        if (eError != PVRSRV_OK)
        {
 
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVAllocSyncInfoKM: Failed to alloc memory"));
+               OSAtomicFree(psKernelSyncInfo->pvRefCount);
                OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(PVRSRV_KERNEL_SYNC_INFO), psKernelSyncInfo, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
                return PVRSRV_ERROR_OUT_OF_MEMORY;
        }
 
-       
+       /* init sync data */
        psKernelSyncInfo->psSyncData = psKernelSyncInfo->psSyncDataMemInfoKM->pvLinAddrKM;
        psSyncData = psKernelSyncInfo->psSyncData;
 
@@ -523,8 +707,11 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocSyncInfoKM(IMG_HANDLE                                 hDevCookie,
        psSyncData->ui32WriteOpsComplete = 0;
        psSyncData->ui32ReadOpsPending = 0;
        psSyncData->ui32ReadOpsComplete = 0;
+       psSyncData->ui32ReadOps2Pending = 0;
+       psSyncData->ui32ReadOps2Complete = 0;
        psSyncData->ui32LastOpDumpVal = 0;
        psSyncData->ui32LastReadOpDumpVal = 0;
+       psSyncData->ui64LastWrite = 0;
 
 #if defined(PDUMP)
        PDUMPCOMMENT("Allocating kernel sync object");
@@ -538,248 +725,172 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVAllocSyncInfoKM(IMG_HANDLE                                      hDevCookie,
 
        psKernelSyncInfo->sWriteOpsCompleteDevVAddr.uiAddr = psKernelSyncInfo->psSyncDataMemInfoKM->sDevVAddr.uiAddr + offsetof(PVRSRV_SYNC_DATA, ui32WriteOpsComplete);
        psKernelSyncInfo->sReadOpsCompleteDevVAddr.uiAddr = psKernelSyncInfo->psSyncDataMemInfoKM->sDevVAddr.uiAddr + offsetof(PVRSRV_SYNC_DATA, ui32ReadOpsComplete);
+       psKernelSyncInfo->sReadOps2CompleteDevVAddr.uiAddr = psKernelSyncInfo->psSyncDataMemInfoKM->sDevVAddr.uiAddr + offsetof(PVRSRV_SYNC_DATA, ui32ReadOps2Complete);
        psKernelSyncInfo->ui32UID = g_ui32SyncUID++;
 
-       
+       /* syncinfo meminfo has no syncinfo! */
        psKernelSyncInfo->psSyncDataMemInfoKM->psKernelSyncInfo = IMG_NULL;
 
-       
+       OSAtomicInc(psKernelSyncInfo->pvRefCount);
+
+       /* return result */
        *ppsKernelSyncInfo = psKernelSyncInfo;
 
        return PVRSRV_OK;
 }
 
-
 IMG_EXPORT
-PVRSRV_ERROR IMG_CALLCONV PVRSRVFreeSyncInfoKM(PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo)
+IMG_VOID PVRSRVAcquireSyncInfoKM(PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo)
 {
-       PVRSRV_ERROR eError;
+       OSAtomicInc(psKernelSyncInfo->pvRefCount);
+}
 
-       if (psKernelSyncInfo->ui32RefCount != 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "oops: sync info ref count not zero at destruction"));
-               
-               return PVRSRV_ERROR_OUT_OF_MEMORY; 
-       }
+/*!
+******************************************************************************
 
-       eError = FreeDeviceMem(psKernelSyncInfo->psSyncDataMemInfoKM);
-       (IMG_VOID)OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(PVRSRV_KERNEL_SYNC_INFO), psKernelSyncInfo, IMG_NULL);
-       
+ @Function     PVRSRVFreeSyncInfoKM
 
-       return eError;
-}
+ @Description
 
-static IMG_VOID freeWrapped(PVRSRV_KERNEL_MEM_INFO *psMemInfo)
-{
-       IMG_HANDLE hOSWrapMem = psMemInfo->sMemBlk.hOSWrapMem;
+ Frees a sync info
 
-       
-       if(psMemInfo->sMemBlk.psIntSysPAddr)
-       {
-               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(IMG_SYS_PHYADDR), psMemInfo->sMemBlk.psIntSysPAddr, IMG_NULL);
-               psMemInfo->sMemBlk.psIntSysPAddr = IMG_NULL;
-       }
+ @Return   PVRSRV_ERROR :
 
-       if(hOSWrapMem)
+******************************************************************************/
+IMG_EXPORT
+IMG_VOID IMG_CALLCONV PVRSRVReleaseSyncInfoKM(PVRSRV_KERNEL_SYNC_INFO  *psKernelSyncInfo)
+{
+       if (OSAtomicDecAndTest(psKernelSyncInfo->pvRefCount))
        {
-               OSReleasePhysPageAddr(hOSWrapMem);
+               FreeDeviceMem(psKernelSyncInfo->psSyncDataMemInfoKM);
+       
+               /* Catch anyone who is trying to access the freed structure */
+               psKernelSyncInfo->psSyncDataMemInfoKM = IMG_NULL;
+               psKernelSyncInfo->psSyncData = IMG_NULL;
+               OSAtomicFree(psKernelSyncInfo->pvRefCount);
+               (IMG_VOID)OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(PVRSRV_KERNEL_SYNC_INFO), psKernelSyncInfo, IMG_NULL);
+               /*not nulling pointer, copy on stack*/
        }
 }
 
+/*!
+******************************************************************************
 
-#if defined (PVRSRV_FLUSH_KERNEL_OPS_LAST_ONLY)
-static
-PVRSRV_ERROR _PollUntilAtLeast(volatile IMG_UINT32* pui32WatchedValue,
-                               IMG_UINT32 ui32MinimumValue,
-                               IMG_UINT32 ui32Waitus,
-                               IMG_UINT32 ui32Tries)
-{
-       PVRSRV_ERROR eError;
-       IMG_INT32 iDiff;
+ @Function     freeExternal
 
-       for(;;)
-       {
-               SYS_DATA *psSysData = SysAcquireDataNoCheck();
-               iDiff = *pui32WatchedValue - ui32MinimumValue;
+ @Description
 
-               if (iDiff >= 0)
-               {
-                       eError = PVRSRV_OK;
-                       break;
-               }
+ Code for freeing meminfo elements that are specific to external types memory
 
-               if(!ui32Tries)
-               {
-                       eError = PVRSRV_ERROR_TIMEOUT_POLLING_FOR_VALUE;
-                       break;
-               }
+ @Input           psMemInfo : Kernel meminfo
 
-               ui32Tries--;
+ @Return   PVRSRV_ERROR :
 
-               
-               if (psSysData->psGlobalEventObject)
-               {
-                       IMG_HANDLE hOSEventKM;
-                       if(psSysData->psGlobalEventObject)
-                       {
-                               eError = OSEventObjectOpenKM(psSysData->psGlobalEventObject, &hOSEventKM);
-                               if (eError |= PVRSRV_OK)
-                               {
-                                       PVR_DPF((PVR_DBG_ERROR,
-                                                               "_PollUntilAtLeast: OSEventObjectOpen failed"));
-                                       goto Exit;
-                               }
-                               eError = OSEventObjectWaitKM(hOSEventKM);
-                               if (eError != PVRSRV_OK)
-                               {
-                                       PVR_DPF((PVR_DBG_ERROR,
-                                                               "_PollUntilAtLeast: PVRSRVEventObjectWait failed"));
-                                       goto Exit;
-                               }
-                               eError = OSEventObjectCloseKM(psSysData->psGlobalEventObject, hOSEventKM);
-                               if (eError != PVRSRV_OK)
-                               {
-                                       PVR_DPF((PVR_DBG_ERROR,
-                                                               "_PollUntilAtLeast: OSEventObjectClose failed"));
-                               }
-                       }
-               }
-       }
-Exit:
-       return eError;
-}
+******************************************************************************/
 
-static PVRSRV_ERROR FlushKernelOps(PVRSRV_SYNC_DATA *psSyncData)
+static IMG_VOID freeExternal(PVRSRV_KERNEL_MEM_INFO *psMemInfo)
 {
-       PVRSRV_ERROR eError;
+       IMG_HANDLE hOSWrapMem = psMemInfo->sMemBlk.hOSWrapMem;
 
-       if(!psSyncData)
+       /* free the page addr array if req'd */
+       if(psMemInfo->sMemBlk.psIntSysPAddr)
        {
-               PVR_DPF((PVR_DBG_ERROR, "FlushKernelOps: invalid psSyncData"));
-               return PVRSRV_ERROR_INVALID_PARAMS;
+               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(IMG_SYS_PHYADDR), psMemInfo->sMemBlk.psIntSysPAddr, IMG_NULL);
+               psMemInfo->sMemBlk.psIntSysPAddr = IMG_NULL;
        }
 
-       
-
-
-
-
+       /* Mem type dependent stuff */
+       if (psMemInfo->memType == PVRSRV_MEMTYPE_WRAPPED)
+       {
+               if(hOSWrapMem)
+               {
+                       OSReleasePhysPageAddr(hOSWrapMem);
+               }
+       }
+#if defined(SUPPORT_ION)
+       else if (psMemInfo->memType == PVRSRV_MEMTYPE_ION)
+       {
+               if (hOSWrapMem)
+               {
+                       IonUnimportBufferAndReleasePhysAddr(hOSWrapMem);
+               }
+       }
+#endif
+}
 
+/*!
+******************************************************************************
 
+ @Function     FreeMemCallBackCommon
 
+ @Description
 
-       eError = _PollUntilAtLeast(&psSyncData->ui32ReadOpsComplete,
-                               psSyncData->ui32ReadOpsPending,
-                               MAX_HW_TIME_US/WAIT_TRY_COUNT,
-                               WAIT_TRY_COUNT);
-       if (eError != PVRSRV_OK)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "FlushClientOps: Read ops pending timeout"));
-               PVR_DBG_BREAK; 
-               return eError;
-       }
+ Common code for freeing device mem (called for freeing, unwrapping and unmapping)
 
-       eError = _PollUntilAtLeast(&psSyncData->ui32WriteOpsComplete,
-                               psSyncData->ui32WriteOpsPending,
-                               MAX_HW_TIME_US/WAIT_TRY_COUNT,
-                               WAIT_TRY_COUNT);
-       if (eError != PVRSRV_OK)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "FlushClientOps: Write ops pending timeout"));
-               PVR_DBG_BREAK; 
-       }
+ @Input           psMemInfo : Kernel meminfo
+ @Input           ui32Param :  packet size
+ @Input           uibFromAllocatorParam :  Are we being called by the original allocator?
 
-       return eError;
-}
-#endif 
+ @Return   PVRSRV_ERROR :
 
-static PVRSRV_ERROR FreeMemCallBackCommon(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
-                                                                                 IMG_UINT32    ui32Param,
-                                                                                 IMG_BOOL      bFromAllocator)
+******************************************************************************/
+IMG_EXPORT
+PVRSRV_ERROR FreeMemCallBackCommon(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
+                                                                  IMG_UINT32   ui32Param,
+                                                                  PVRSRV_FREE_CALLBACK_ORIGIN eCallbackOrigin)
 {
        PVRSRV_ERROR eError = PVRSRV_OK;
 
        PVR_UNREFERENCED_PARAMETER(ui32Param);
 
-       
-       psMemInfo->ui32RefCount--;
+       /* decrement the refcount */
+       PVRSRVKernelMemInfoDecRef(psMemInfo);
 
-       
-       if(((psMemInfo->ui32Flags & PVRSRV_MEM_EXPORTED) != 0) && (bFromAllocator == IMG_TRUE))
+       /* check no other processes has this meminfo mapped */
+       if (psMemInfo->ui32RefCount == 0)
        {
+               if((psMemInfo->ui32Flags & PVRSRV_MEM_EXPORTED) != 0)
+               {
 #if defined (SUPPORT_SID_INTERFACE)
-               IMG_SID hMemInfo = 0;
+                       IMG_SID hMemInfo = 0;
 #else
-               IMG_HANDLE hMemInfo = IMG_NULL;
+                       IMG_HANDLE hMemInfo = IMG_NULL;
 #endif
 
-               
-               eError = PVRSRVFindHandle(KERNEL_HANDLE_BASE,
-                                                                &hMemInfo,
-                                                                psMemInfo,
-                                                                PVRSRV_HANDLE_TYPE_MEM_INFO);
-               if(eError != PVRSRV_OK)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "FreeMemCallBackCommon: can't find exported meminfo in the global handle list"));
-                       return eError;
-               }
-
-               
-               eError = PVRSRVReleaseHandle(KERNEL_HANDLE_BASE,
-                                                                       hMemInfo,
-                                                                       PVRSRV_HANDLE_TYPE_MEM_INFO);
-               if(eError != PVRSRV_OK)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "FreeMemCallBackCommon: PVRSRVReleaseHandle failed for exported meminfo"));
-                       return eError;
-               }
-       }
-
-       
-       if (psMemInfo->ui32RefCount == 0)
-       {
-#if defined (PVRSRV_FLUSH_KERNEL_OPS_LAST_ONLY)
-               if (psMemInfo->psKernelSyncInfo)
-               {
-                       if (psMemInfo->sShareMemWorkaround.bInUse)
+                       /* find the handle */
+                       eError = PVRSRVFindHandle(KERNEL_HANDLE_BASE,
+                                                                        &hMemInfo,
+                                                                        psMemInfo,
+                                                                        PVRSRV_HANDLE_TYPE_MEM_INFO);
+                       if(eError != PVRSRV_OK)
                        {
-                               
-                               if (BM_XProcWorkaroundGetRefCount(psMemInfo->sShareMemWorkaround.ui32ShareIndex)
-                                               == 1)
-                               {
-                                       FlushKernelOps(psMemInfo->psKernelSyncInfo->psSyncData);
-                               }
+                               PVR_DPF((PVR_DBG_ERROR, "FreeMemCallBackCommon: can't find exported meminfo in the global handle list"));
+                               return eError;
                        }
-                       else
-                       {
-                               
-
-
-
-
-
-
 
-                               FlushKernelOps(psMemInfo->psKernelSyncInfo->psSyncData);
+                       /* release the handle */
+                       eError = PVRSRVReleaseHandle(KERNEL_HANDLE_BASE,
+                                                                               hMemInfo,
+                                                                               PVRSRV_HANDLE_TYPE_MEM_INFO);
+                       if(eError != PVRSRV_OK)
+                       {
+                               PVR_DPF((PVR_DBG_ERROR, "FreeMemCallBackCommon: PVRSRVReleaseHandle failed for exported meminfo"));
+                               return eError;
                        }
                }
-#endif
+
                switch(psMemInfo->memType)
                {
-                       
+                       /* Fall through: Free only what we should for each memory type */
                        case PVRSRV_MEMTYPE_WRAPPED:
-                               freeWrapped(psMemInfo);
+                       case PVRSRV_MEMTYPE_ION:
+                               freeExternal(psMemInfo);
                        case PVRSRV_MEMTYPE_DEVICE:
+                       case PVRSRV_MEMTYPE_DEVICECLASS:
                                if (psMemInfo->psKernelSyncInfo)
                                {
-                                       psMemInfo->psKernelSyncInfo->ui32RefCount--;
-
-                                       if (psMemInfo->psKernelSyncInfo->ui32RefCount == 0)
-                                       {
-                                               eError = PVRSRVFreeSyncInfoKM(psMemInfo->psKernelSyncInfo);
-                                       }
+                                       PVRSRVKernelSyncInfoDecRef(psMemInfo->psKernelSyncInfo, psMemInfo);
                                }
-                       case PVRSRV_MEMTYPE_DEVICECLASS:
                                break;
                        default:
                                PVR_DPF((PVR_DBG_ERROR, "FreeMemCallBackCommon: Unknown memType"));
@@ -787,15 +898,36 @@ static PVRSRV_ERROR FreeMemCallBackCommon(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
                }
        }
 
-       
+       /*
+        * FreeDeviceMem2 will do the right thing, freeing
+        * the virtual memory info when the allocator calls
+        * but only releaseing the physical pages when everyone
+        * is done.
+        */
+
        if (eError == PVRSRV_OK)
        {
-               eError = FreeDeviceMem2(psMemInfo, bFromAllocator);
+               eError = FreeDeviceMem2(psMemInfo, eCallbackOrigin);
        }
 
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     FreeDeviceMemCallBack
+
+ @Description
+
+ ResMan call back to free device memory
+
+ @Input           pvParam : data packet
+ @Input           ui32Param :  packet size
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 static PVRSRV_ERROR FreeDeviceMemCallBack(IMG_PVOID  pvParam,
                                                                                  IMG_UINT32 ui32Param,
                                                                                  IMG_BOOL   bDummy)
@@ -804,10 +936,25 @@ static PVRSRV_ERROR FreeDeviceMemCallBack(IMG_PVOID  pvParam,
        
        PVR_UNREFERENCED_PARAMETER(bDummy);
 
-       return FreeMemCallBackCommon(psMemInfo, ui32Param, IMG_TRUE);
+       return FreeMemCallBackCommon(psMemInfo, ui32Param,
+                                                                PVRSRV_FREE_CALLBACK_ORIGIN_ALLOCATOR);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVFreeDeviceMemKM
+
+ @Description
+
+ Frees memory allocated with PVRAllocDeviceMem, including the mem_info structure
+
+ @Input           psMemInfo :
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVFreeDeviceMemKM(IMG_HANDLE                             hDevCookie,
                                                                                                PVRSRV_KERNEL_MEM_INFO  *psMemInfo)
@@ -827,7 +974,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVFreeDeviceMemKM(IMG_HANDLE                          hDevCookie,
        }
        else
        {
-               
+               /* PVRSRV_MEM_NO_RESMAN */
                eError = FreeDeviceMemCallBack(psMemInfo, 0, CLEANUP_WITH_POLL);
        }
 
@@ -835,14 +982,40 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVFreeDeviceMemKM(IMG_HANDLE                                hDevCookie,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVAllocDeviceMemKM
+
+ @Description
+
+ Allocates device memory
+
+ @Input           hDevCookie :
+ @Input           psPerProc : Per-process data
+ @Input           hDevMemHeap
+ @Input           ui32Flags : Some combination of PVRSRV_MEM_ flags
+ @Input           ui32Size :  Number of bytes to allocate
+ @Input           ui32Alignment :
+ @Output   **ppsMemInfo : On success, receives a pointer to the created MEM_INFO structure
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
-PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                                   hDevCookie,
-                                                                                                PVRSRV_PER_PROCESS_DATA        *psPerProc,
-                                                                                                IMG_HANDLE                                     hDevMemHeap,
-                                                                                                IMG_UINT32                                     ui32Flags,
-                                                                                                IMG_SIZE_T                                     ui32Size,
-                                                                                                IMG_SIZE_T                                     ui32Alignment,
-                                                                                                PVRSRV_KERNEL_MEM_INFO         **ppsMemInfo)
+PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                           hDevCookie,
+                                                                                                 PVRSRV_PER_PROCESS_DATA       *psPerProc,
+                                                                                                 IMG_HANDLE                            hDevMemHeap,
+                                                                                                 IMG_UINT32                            ui32Flags,
+                                                                                                 IMG_SIZE_T                            ui32Size,
+                                                                                                 IMG_SIZE_T                            ui32Alignment,
+                                                                                                 IMG_PVOID                                     pvPrivData,
+                                                                                                 IMG_UINT32                            ui32PrivDataLength,
+                                                                                                 IMG_UINT32                            ui32ChunkSize,
+                                                                                                 IMG_UINT32                            ui32NumVirtChunks,
+                                                                                                 IMG_UINT32                            ui32NumPhysChunks,
+                                                                                                 IMG_BOOL                                      *pabMapChunk,
+                                                                                                 PVRSRV_KERNEL_MEM_INFO        **ppsMemInfo)
 {
        PVRSRV_KERNEL_MEM_INFO  *psMemInfo;
        PVRSRV_ERROR                    eError;
@@ -850,15 +1023,46 @@ PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                                     hDevCookie,
        IMG_HANDLE                              hDevMemContext;
 
        if (!hDevMemHeap ||
-               (ui32Size == 0))
+               ((ui32Size == 0) && ((ui32Flags & PVRSRV_MEM_SPARSE) == 0)) ||
+               (((ui32ChunkSize == 0) || (ui32NumVirtChunks == 0) || (ui32NumPhysChunks == 0) ||
+               (pabMapChunk == IMG_NULL )) && (ui32Flags & PVRSRV_MEM_SPARSE)))
        {
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* Sprase alloc input validation */
+       if (ui32Flags & PVRSRV_MEM_SPARSE)
+       {
+               IMG_UINT32 i;
+               IMG_UINT32 ui32Check = 0;
+
+               if (ui32NumVirtChunks < ui32NumPhysChunks)
+               {
+                       return PVRSRV_ERROR_INVALID_PARAMS;
+               }
+
+               for (i=0;i<ui32NumVirtChunks;i++)
+               {
+                       if (pabMapChunk[i])
+                       {
+                               ui32Check++;
+                       }
+               }
+               if (ui32NumPhysChunks != ui32Check)
+               {
+                       return PVRSRV_ERROR_INVALID_PARAMS;
+               }
+       }
+
+       /* FIXME: At the moment we force CACHETYPE override allocations to
+        *        be multiples of PAGE_SIZE and page aligned. If the RA/BM
+        *        is fixed, this limitation can be removed.
+        *
+        * INTEGRATION_POINT: HOST_PAGESIZE() is not correct, should be device-specific.
+        */
        if (ui32Flags & PVRSRV_HAP_CACHETYPE_MASK)
        {
-                
+               /* PRQA S 3415 1 */ /* order of evaluation is not important */
                if (((ui32Size % HOST_PAGESIZE()) != 0) ||
                        ((ui32Alignment % HOST_PAGESIZE()) != 0))
                {
@@ -871,6 +1075,12 @@ PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                                      hDevCookie,
                                                        ui32Flags,
                                                        ui32Size,
                                                        ui32Alignment,
+                                                       pvPrivData,
+                                                       ui32PrivDataLength,
+                                                       ui32ChunkSize,
+                                                       ui32NumVirtChunks,
+                                                       ui32NumPhysChunks,
+                                                       pabMapChunk,
                                                        &psMemInfo);
 
        if (eError != PVRSRV_OK)
@@ -884,9 +1094,10 @@ PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                                      hDevCookie,
        }
        else
        {
-               
-
-
+               /*
+                       allocate a syncinfo but don't register with resman
+                       because the holding devicemem will handle the syncinfo
+               */
                psBMHeap = (BM_HEAP*)hDevMemHeap;
                hDevMemContext = (IMG_HANDLE)psBMHeap->pBMContext;
                eError = PVRSRVAllocSyncInfoKM(hDevCookie,
@@ -896,10 +1107,11 @@ PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                                     hDevCookie,
                {
                        goto free_mainalloc;
                }
-               psMemInfo->psKernelSyncInfo->ui32RefCount++;
        }
 
-       
+       /*
+        * Setup the output.
+        */
        *ppsMemInfo = psMemInfo;
 
        if (ui32Flags & PVRSRV_MEM_NO_RESMAN)
@@ -908,7 +1120,7 @@ PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                                       hDevCookie,
        }
        else
        {
-               
+               /* register with the resman */
                psMemInfo->sMemBlk.hResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                                                                RESMAN_TYPE_DEVICEMEM_ALLOCATION,
                                                                                                                psMemInfo,
@@ -916,27 +1128,282 @@ PVRSRV_ERROR IMG_CALLCONV _PVRSRVAllocDeviceMemKM(IMG_HANDLE                                    hDevCookie,
                                                                                                                &FreeDeviceMemCallBack);
                if (psMemInfo->sMemBlk.hResItem == IMG_NULL)
                {
-                       
                        eError = PVRSRV_ERROR_OUT_OF_MEMORY;
                        goto free_mainalloc;
                }
        }
 
-       
-       psMemInfo->ui32RefCount++;
+       /* increment the refcount */
+       PVRSRVKernelMemInfoIncRef(psMemInfo);
 
        psMemInfo->memType = PVRSRV_MEMTYPE_DEVICE;
 
-       
+       /*
+        * And I think we're done for now....
+        */
        return (PVRSRV_OK);
 
 free_mainalloc:
+       if (psMemInfo->psKernelSyncInfo)
+       {
+               PVRSRVKernelSyncInfoDecRef(psMemInfo->psKernelSyncInfo, psMemInfo);
+       }
        FreeDeviceMem(psMemInfo);
 
        return eError;
 }
 
+#if defined(SUPPORT_ION)
+static PVRSRV_ERROR IonUnmapCallback(IMG_PVOID  pvParam,
+                                                                        IMG_UINT32 ui32Param,
+                                                                        IMG_BOOL   bDummy)
+{
+       PVRSRV_KERNEL_MEM_INFO  *psMemInfo = (PVRSRV_KERNEL_MEM_INFO *)pvParam;
+       
+       PVR_UNREFERENCED_PARAMETER(bDummy);
+
+       return FreeMemCallBackCommon(psMemInfo, ui32Param, PVRSRV_FREE_CALLBACK_ORIGIN_ALLOCATOR);
+}
+
+/*!
+******************************************************************************
+
+ @Function     PVRSRVMapIonHandleKM
+
+ @Description
+
+ Map an ION buffer into the specified device memory context
+
+ @Input           psPerProc : PerProcess data
+ @Input    hDevCookie : Device node cookie
+ @Input    hDevMemContext : Device memory context cookie
+ @Input    hIon : Handle to ION buffer
+ @Input    ui32Flags : Mapping flags
+ @Input    ui32Size : Mapping size
+ @Output   ppsKernelMemInfo: Output kernel meminfo if successful
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
+IMG_EXPORT
+PVRSRV_ERROR PVRSRVMapIonHandleKM(PVRSRV_PER_PROCESS_DATA *psPerProc,
+                                                                 IMG_HANDLE hDevCookie,
+                                                                 IMG_HANDLE hDevMemContext,
+                                                                 IMG_HANDLE hIon,
+                                                                 IMG_UINT32 ui32Flags,
+                                                                 IMG_UINT32 ui32Size,
+                                                                 PVRSRV_KERNEL_MEM_INFO **ppsKernelMemInfo)
+{
+       PVRSRV_ENV_PER_PROCESS_DATA *psPerProcEnv = PVRSRVProcessPrivateData(psPerProc);
+       PVRSRV_DEVICE_NODE *psDeviceNode; 
+       PVRSRV_KERNEL_MEM_INFO *psNewKernelMemInfo;
+       DEVICE_MEMORY_INFO *psDevMemoryInfo;
+       DEVICE_MEMORY_HEAP_INFO *psDeviceMemoryHeap;
+       IMG_SYS_PHYADDR *pasSysPhysAddr;
+       PVRSRV_MEMBLK *psMemBlock;
+       PVRSRV_ERROR eError;
+       IMG_HANDLE hDevMemHeap = IMG_NULL;
+       IMG_HANDLE hPriv;
+       BM_HANDLE hBuffer;
+       IMG_UINT32 ui32HeapCount;
+       IMG_UINT32 ui32PageCount;
+       IMG_UINT32 i;
+       IMG_BOOL bAllocSync = (ui32Flags & PVRSRV_MEM_NO_SYNCOBJ)?IMG_FALSE:IMG_TRUE;
+
+       if ((hDevCookie == IMG_NULL) || (ui32Size == 0)
+                || (hDevMemContext == IMG_NULL) || (ppsKernelMemInfo == IMG_NULL))
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: Invalid params", __FUNCTION__));
+               return PVRSRV_ERROR_INVALID_PARAMS;
+       }
+
+       psDeviceNode = (PVRSRV_DEVICE_NODE *)hDevCookie;
+
+       if(OSAllocMem(PVRSRV_PAGEABLE_SELECT,
+                                       sizeof(PVRSRV_KERNEL_MEM_INFO),
+                                       (IMG_VOID **)&psNewKernelMemInfo, IMG_NULL,
+                                       "Kernel Memory Info") != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"%s: Failed to alloc memory for block", __FUNCTION__));
+               return PVRSRV_ERROR_OUT_OF_MEMORY;
+       }
+       OSMemSet(psNewKernelMemInfo, 0, sizeof(PVRSRV_KERNEL_MEM_INFO));
+
+       /* Choose the heap to map to */
+       ui32HeapCount = psDeviceNode->sDevMemoryInfo.ui32HeapCount;
+       psDevMemoryInfo = &psDeviceNode->sDevMemoryInfo;
+       psDeviceMemoryHeap = psDeviceNode->sDevMemoryInfo.psDeviceMemoryHeap;   
+       for(i=0; i<PVRSRV_MAX_CLIENT_HEAPS; i++)
+       {
+               if(HEAP_IDX(psDeviceMemoryHeap[i].ui32HeapID) == psDevMemoryInfo->ui32IonHeapID)
+               {
+                       if(psDeviceMemoryHeap[i].DevMemHeapType == DEVICE_MEMORY_HEAP_PERCONTEXT)
+                       {
+                               if (psDeviceMemoryHeap[i].ui32HeapSize > 0)
+                               {
+                                       hDevMemHeap = BM_CreateHeap(hDevMemContext, &psDeviceMemoryHeap[i]);
+                               }
+                               else
+                               {
+                                       hDevMemHeap = IMG_NULL;
+                               }
+                       }
+                       else
+                       {
+                               hDevMemHeap = psDevMemoryInfo->psDeviceMemoryHeap[i].hDevMemHeap;
+                       }
+                       break;
+               }
+       }
+       
+       if (hDevMemHeap == IMG_NULL)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: Failed to get ION heap", __FUNCTION__));
+               eError = PVRSRV_ERROR_FAILED_TO_RETRIEVE_HEAPINFO;
+               goto exitFailedHeap;
+       }
+
+       /* Import the ION buffer into our ion_client and DMA map it */
+       eError = IonImportBufferAndAquirePhysAddr(psPerProcEnv->psIONClient,
+                                                                                         hIon,
+                                                                                         &ui32PageCount,
+                                                                                         &pasSysPhysAddr,
+                                                                                         &psNewKernelMemInfo->pvLinAddrKM,
+                                                                                         &hPriv);
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: Failed to get ion buffer/buffer phys addr", __FUNCTION__));
+               goto exitFailedHeap;
+       }
+
+       /* Wrap the returned addresses into our memory context */
+       if (!BM_Wrap(hDevMemHeap,
+                                ui32Size,
+                                0,
+                                IMG_FALSE,
+                                pasSysPhysAddr,
+                                IMG_NULL,
+                                &ui32Flags,    /* This function clobbers our bits in ui32Flags */
+                                &hBuffer))
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: Failed to wrap ion buffer", __FUNCTION__));
+               eError = PVRSRV_ERROR_OUT_OF_MEMORY;
+               goto exitFailedWrap;
+       }
+
+       /* Fill in "Implementation dependant" section of mem info */
+       psMemBlock = &psNewKernelMemInfo->sMemBlk;
+       psMemBlock->sDevVirtAddr = BM_HandleToDevVaddr(hBuffer);
+       psMemBlock->hOSMemHandle = BM_HandleToOSMemHandle(hBuffer);
+       psMemBlock->hBuffer = (IMG_HANDLE) hBuffer;
+       psMemBlock->hOSWrapMem = hPriv;                 /* Saves creating a new element as we know hOSWrapMem will not be used */
+       psMemBlock->psIntSysPAddr = pasSysPhysAddr;
+
+       psNewKernelMemInfo->ui32Flags = ui32Flags;
+       psNewKernelMemInfo->sDevVAddr = psMemBlock->sDevVirtAddr;
+       psNewKernelMemInfo->uAllocSize = ui32Size;
+       psNewKernelMemInfo->memType = PVRSRV_MEMTYPE_ION;
+       PVRSRVKernelMemInfoIncRef(psNewKernelMemInfo);
+
+       /* Clear the Backup buffer pointer as we do not have one at this point. We only allocate this as we are going up/down */
+       psNewKernelMemInfo->pvSysBackupBuffer = IMG_NULL;
+
+       if (!bAllocSync)
+       {
+               psNewKernelMemInfo->psKernelSyncInfo = IMG_NULL;
+       }
+       else
+       {
+               eError = PVRSRVAllocSyncInfoKM(hDevCookie,
+                                                                          hDevMemContext,
+                                                                          &psNewKernelMemInfo->psKernelSyncInfo);
+               if(eError != PVRSRV_OK)
+               {
+                       goto exitFailedSync;
+               }
+       }
+
+       /* register with the resman */
+       psNewKernelMemInfo->sMemBlk.hResItem = ResManRegisterRes(psPerProc->hResManContext,
+                                                                                                                        RESMAN_TYPE_DEVICEMEM_ION,
+                                                                                                                        psNewKernelMemInfo,
+                                                                                                                        0,
+                                                                                                                        &IonUnmapCallback);
+       if (psNewKernelMemInfo->sMemBlk.hResItem == IMG_NULL)
+       {
+               eError = PVRSRV_ERROR_OUT_OF_MEMORY;
+               goto exitFailedResman;
+       }
+
+       psNewKernelMemInfo->memType = PVRSRV_MEMTYPE_ION;
+
+       *ppsKernelMemInfo = psNewKernelMemInfo;
+       return PVRSRV_OK;
+
+exitFailedResman:
+       if (psNewKernelMemInfo->psKernelSyncInfo)
+       {
+               PVRSRVKernelSyncInfoDecRef(psNewKernelMemInfo->psKernelSyncInfo, psNewKernelMemInfo);
+       }
+exitFailedSync:
+       BM_Free(hBuffer, ui32Flags);
+exitFailedWrap:
+       IonUnimportBufferAndReleasePhysAddr(hPriv);
+       OSFreeMem(PVRSRV_PAGEABLE_SELECT,
+                         sizeof(IMG_SYS_PHYADDR) * ui32PageCount,
+                         pasSysPhysAddr,
+                         IMG_NULL);
+exitFailedHeap:
+       OSFreeMem(PVRSRV_PAGEABLE_SELECT,
+                         sizeof(PVRSRV_KERNEL_MEM_INFO),
+                         psNewKernelMemInfo,
+                         IMG_NULL);
+
+       return eError;
+}
+
+/*!
+******************************************************************************
+
+ @Function     PVRSRVUnmapIonHandleKM
+
+ @Description
+
+ Frees an ion buffer mapped with PVRSRVMapIonHandleKM, including the mem_info structure
+
+ @Input           psMemInfo :
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
+IMG_EXPORT
+PVRSRV_ERROR IMG_CALLCONV PVRSRVUnmapIonHandleKM(PVRSRV_KERNEL_MEM_INFO *psMemInfo)
+{
+       if (!psMemInfo)
+       {
+               return PVRSRV_ERROR_INVALID_PARAMS;
+       }
+
+       return ResManFreeResByPtr(psMemInfo->sMemBlk.hResItem, CLEANUP_WITH_POLL);
+}
+#endif /* SUPPORT_ION */
+
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDissociateDeviceMemKM
 
+ @Description
+
+ Dissociates memory from the process that allocates it.  Intended for
+ transfering the ownership of device memory from a particular process
+ to the kernel.
+
+ @Input           psMemInfo :
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVDissociateDeviceMemKM(IMG_HANDLE              hDevCookie,
                                                                                                          PVRSRV_KERNEL_MEM_INFO *psMemInfo)
@@ -959,13 +1426,34 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDissociateDeviceMemKM(IMG_HANDLE              hD
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVGetFreeDeviceMemKM
+
+ @Description
+
+ Determines how much memory remains available in the system with the specified
+ capabilities.
+
+ @Input           ui32Flags :
+
+ @Output   pui32Total :
+
+ @Output   pui32Free :
+
+ @Output   pui32LargestBlock :
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetFreeDeviceMemKM(IMG_UINT32 ui32Flags,
                                                                                                   IMG_SIZE_T *pui32Total,
                                                                                                   IMG_SIZE_T *pui32Free,
                                                                                                   IMG_SIZE_T *pui32LargestBlock)
 {
-       
+       /* TO BE IMPLEMENTED */
 
        PVR_UNREFERENCED_PARAMETER(ui32Flags);
        PVR_UNREFERENCED_PARAMETER(pui32Total);
@@ -978,6 +1466,17 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetFreeDeviceMemKM(IMG_UINT32 ui32Flags,
 
 
 
+/*!
+******************************************************************************
+       @Function   PVRSRVUnwrapExtMemoryKM
+
+       @Description  On last unwrap of a given meminfo, unmaps physical pages from a
+                               wrapped allocation, and frees the associated device address space.
+                               Note: this can only unmap memory mapped by PVRSRVWrapExtMemory
+
+       @Input      psMemInfo - mem info describing the wrapped allocation
+       @Return     None
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVUnwrapExtMemoryKM (PVRSRV_KERNEL_MEM_INFO      *psMemInfo)
 {
@@ -990,6 +1489,16 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVUnwrapExtMemoryKM (PVRSRV_KERNEL_MEM_INFO *psMem
 }
 
 
+/*!
+******************************************************************************
+       @Function   UnwrapExtMemoryCallBack
+
+       @Description Resman callback to unwrap memory
+
+       @Input      pvParam - opaque void ptr param
+       @Input      ui32Param - opaque unsigned long param
+       @Return     PVRSRV_ERROR
+******************************************************************************/
 static PVRSRV_ERROR UnwrapExtMemoryCallBack(IMG_PVOID  pvParam,
                                                                                        IMG_UINT32 ui32Param,
                                                                                        IMG_BOOL   bDummy)
@@ -998,10 +1507,31 @@ static PVRSRV_ERROR UnwrapExtMemoryCallBack(IMG_PVOID  pvParam,
        
        PVR_UNREFERENCED_PARAMETER(bDummy);
 
-       return FreeMemCallBackCommon(psMemInfo, ui32Param, IMG_TRUE);
+       return FreeMemCallBackCommon(psMemInfo, ui32Param,
+                                                                PVRSRV_FREE_CALLBACK_ORIGIN_ALLOCATOR);
 }
 
 
+/*!
+******************************************************************************
+       @Function   PVRSRVWrapExtMemoryKM
+
+       @Description  Allocates a Device Virtual Address in the shared mapping heap
+                               and maps physical pages into that allocation. Note, if the pages are
+                               already mapped into the heap, the existing allocation is returned.
+
+       @Input      hDevCookie - Device cookie
+       @Input      psPerProc - Per-process data
+       @Input      hDevMemContext - device memory context
+       @Input      uByteSize - Size of allocation
+       @Input      uPageOffset - Offset into the first page of the memory to be wrapped
+       @Input      bPhysContig - whether the underlying memory is physically contiguous
+       @Input      psExtSysPAddr - The list of Device Physical page addresses
+       @Input      pvLinAddr - ptr to buffer to wrap
+       @Output     ppsMemInfo - mem info describing the wrapped allocation
+       @Return     None
+******************************************************************************/
+
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVWrapExtMemoryKM(IMG_HANDLE                             hDevCookie,
                                                                                                PVRSRV_PER_PROCESS_DATA *psPerProc,
@@ -1043,14 +1573,14 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVWrapExtMemoryKM(IMG_HANDLE                              hDevCookie,
 
        if(pvLinAddr)
        {
-               
+               /* derive the page offset from the cpu ptr (in case it's not supplied) */
                uPageOffset = (IMG_UINTPTR_T)pvLinAddr & (ui32HostPageSize - 1);
 
-               
+               /* get the pagecount and the page aligned base ptr */
                uPageCount = HOST_PAGEALIGN(uByteSize + uPageOffset) / ui32HostPageSize;
                pvPageAlignedCPUVAddr = (IMG_VOID *)((IMG_UINTPTR_T)pvLinAddr - uPageOffset);
 
-               
+               /* allocate array of SysPAddr to hold page addresses */
                if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                                uPageCount * sizeof(IMG_SYS_PHYADDR),
                                                (IMG_VOID **)&psIntSysPAddr, IMG_NULL,
@@ -1067,23 +1597,20 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVWrapExtMemoryKM(IMG_HANDLE                              hDevCookie,
                if(eError != PVRSRV_OK)
                {
                        PVR_DPF((PVR_DBG_ERROR,"PVRSRVWrapExtMemoryKM: Failed to alloc memory for block"));
-                       eError = PVRSRV_ERROR_OUT_OF_MEMORY;
+                       eError = PVRSRV_ERROR_OUT_OF_MEMORY;//FIXME: need better error code
                        goto ErrorExitPhase1;
                }
 
-               
+               /* replace the supplied page address list */
                psExtSysPAddr = psIntSysPAddr;
 
-               
-
+               /* assume memory is not physically contiguous;
+                  we shouldn't trust what the user says here
+               */
                bPhysContig = IMG_FALSE;
        }
-       else
-       {
-               
-       }
 
-       
+       /* Choose the heap to map to */
        psDevMemoryInfo = &((BM_CONTEXT*)hDevMemContext)->psDeviceNode->sDevMemoryInfo;
        psDeviceMemoryHeap = psDevMemoryInfo->psDeviceMemoryHeap;
        for(i=0; i<PVRSRV_MAX_CLIENT_HEAPS; i++)
@@ -1092,7 +1619,6 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVWrapExtMemoryKM(IMG_HANDLE                                hDevCookie,
                {
                        if(psDeviceMemoryHeap[i].DevMemHeapType == DEVICE_MEMORY_HEAP_PERCONTEXT)
                        {
-                               
                                if (psDeviceMemoryHeap[i].ui32HeapSize > 0)
                                {
                                        hDevMemHeap = BM_CreateHeap(hDevMemContext, &psDeviceMemoryHeap[i]);
@@ -1147,27 +1673,29 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVWrapExtMemoryKM(IMG_HANDLE                              hDevCookie,
                goto ErrorExitPhase3;
        }
 
-       
+       /* Fill in "Implementation dependant" section of mem info */
        psMemBlock->sDevVirtAddr = BM_HandleToDevVaddr(hBuffer);
        psMemBlock->hOSMemHandle = BM_HandleToOSMemHandle(hBuffer);
        psMemBlock->hOSWrapMem = hOSWrapMem;
        psMemBlock->psIntSysPAddr = psIntSysPAddr;
 
-       
+       /* Convert from BM_HANDLE to external IMG_HANDLE */
        psMemBlock->hBuffer = (IMG_HANDLE)hBuffer;
 
-       
+       /* Fill in the public fields of the MEM_INFO structure */
        psMemInfo->pvLinAddrKM = BM_HandleToCpuVaddr(hBuffer);
        psMemInfo->sDevVAddr = psMemBlock->sDevVirtAddr;
        psMemInfo->uAllocSize = uByteSize;
 
-       
-
+       /* Clear the Backup buffer pointer as we do not have one at this point.
+          We only allocate this as we are going up/down
+        */
        psMemInfo->pvSysBackupBuffer = IMG_NULL;
 
-       
-
-
+       /*
+               allocate a syncinfo but don't register with resman
+               because the holding devicemem will handle the syncinfo
+       */
        psBMHeap = (BM_HEAP*)hDevMemHeap;
        hDevMemContext = (IMG_HANDLE)psBMHeap->pBMContext;
        eError = PVRSRVAllocSyncInfoKM(hDevCookie,
@@ -1178,34 +1706,33 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVWrapExtMemoryKM(IMG_HANDLE                              hDevCookie,
                goto ErrorExitPhase4;
        }
 
-       psMemInfo->psKernelSyncInfo->ui32RefCount++;
-
-       
-       psMemInfo->ui32RefCount++;
+       /* increment the refcount */
+       PVRSRVKernelMemInfoIncRef(psMemInfo);
 
        psMemInfo->memType = PVRSRV_MEMTYPE_WRAPPED;
 
-       
+       /* Register Resource */
        psMemInfo->sMemBlk.hResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                                                        RESMAN_TYPE_DEVICEMEM_WRAP,
                                                                                                        psMemInfo,
                                                                                                        0,
                                                                                                        &UnwrapExtMemoryCallBack);
 
-       
+       /* return the meminfo */
        *ppsMemInfo = psMemInfo;
 
        return PVRSRV_OK;
 
-       
+       /* error handling: */
 
 ErrorExitPhase4:
        if(psMemInfo)
        {
                FreeDeviceMem(psMemInfo);
-               
-
-
+               /*
+                       FreeDeviceMem will free the meminfo so set
+                       it to NULL to avoid double free below
+               */
                psMemInfo = IMG_NULL;
        }
 
@@ -1213,7 +1740,7 @@ ErrorExitPhase3:
        if(psMemInfo)
        {
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_KERNEL_MEM_INFO), psMemInfo, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
        }
 
 ErrorExitPhase2:
@@ -1226,13 +1753,26 @@ ErrorExitPhase1:
        if(psIntSysPAddr)
        {
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, uPageCount * sizeof(IMG_SYS_PHYADDR), psIntSysPAddr, IMG_NULL);
-               
+               /*not nulling shared pointer, uninitialized to this point*/
        }
 
        return eError;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVUnmapDeviceMemoryKM
+
+ @Description
+               Unmaps an existing allocation previously mapped by PVRSRVMapDeviceMemory
+
+ @Input    psMemInfo
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVUnmapDeviceMemoryKM (PVRSRV_KERNEL_MEM_INFO *psMemInfo)
 {
@@ -1245,6 +1785,17 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVUnmapDeviceMemoryKM (PVRSRV_KERNEL_MEM_INFO *psM
 }
 
 
+/*!
+******************************************************************************
+       @Function   UnmapDeviceMemoryCallBack
+
+       @Description Resman callback to unmap memory memory previously mapped
+                               from one allocation to another
+
+       @Input      pvParam - opaque void ptr param
+       @Input      ui32Param - opaque unsigned long param
+       @Return     PVRSRV_ERROR
+******************************************************************************/
 static PVRSRV_ERROR UnmapDeviceMemoryCallBack(IMG_PVOID  pvParam,
                                                                                          IMG_UINT32 ui32Param,
                                                                                          IMG_BOOL   bDummy)
@@ -1263,16 +1814,7 @@ static PVRSRV_ERROR UnmapDeviceMemoryCallBack(IMG_PVOID  pvParam,
 
        if( psMapData->psMemInfo->psKernelSyncInfo )
        {
-               psMapData->psMemInfo->psKernelSyncInfo->ui32RefCount--;
-               if (psMapData->psMemInfo->psKernelSyncInfo->ui32RefCount == 0)
-               {
-                       eError = PVRSRVFreeSyncInfoKM(psMapData->psMemInfo->psKernelSyncInfo);
-                       if(eError != PVRSRV_OK)
-                       {
-                               PVR_DPF((PVR_DBG_ERROR,"UnmapDeviceMemoryCallBack: Failed to free sync info"));
-                               return eError;
-                       }
-               }
+               PVRSRVKernelSyncInfoDecRef(psMapData->psMemInfo->psKernelSyncInfo, psMapData->psMemInfo);
        }
 
        eError = FreeDeviceMem(psMapData->psMemInfo);
@@ -1282,16 +1824,34 @@ static PVRSRV_ERROR UnmapDeviceMemoryCallBack(IMG_PVOID  pvParam,
                return eError;
        }
 
-       
-       eError = FreeMemCallBackCommon(psMapData->psSrcMemInfo, 0, IMG_FALSE);
+       /* This will only free the src psMemInfo if we hold the last reference */
+       eError = FreeMemCallBackCommon(psMapData->psSrcMemInfo, 0,
+                                                                  PVRSRV_FREE_CALLBACK_ORIGIN_IMPORTER);
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(RESMAN_MAP_DEVICE_MEM_DATA), psMapData, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        return eError;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVMapDeviceMemoryKM
+
+ @Description
+               Maps an existing allocation to a specific device address space and heap
+               Note: it's valid to map from one physical device to another
+
+ @Input           psPerProc : Per-process data
+ @Input    psSrcMemInfo
+ @Input    hDstDevMemHeap
+ @Input    ppsDstMemInfo
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceMemoryKM(PVRSRV_PER_PROCESS_DATA      *psPerProc,
                                                                                                  PVRSRV_KERNEL_MEM_INFO        *psSrcMemInfo,
@@ -1314,24 +1874,23 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceMemoryKM(PVRSRV_PER_PROCESS_DATA       *psPer
        IMG_VOID                                        *pvPageAlignedCPUVAddr;
        RESMAN_MAP_DEVICE_MEM_DATA      *psMapData = IMG_NULL;
 
-       
+       /* check params */
        if(!psSrcMemInfo || !hDstDevMemHeap || !ppsDstMemInfo)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVMapDeviceMemoryKM: invalid parameters"));
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* initialise the Dst Meminfo to NULL*/
        *ppsDstMemInfo = IMG_NULL;
 
        uPageOffset = psSrcMemInfo->sDevVAddr.uiAddr & (ui32HostPageSize - 1);
        uPageCount = HOST_PAGEALIGN(psSrcMemInfo->uAllocSize + uPageOffset) / ui32HostPageSize;
        pvPageAlignedCPUVAddr = (IMG_VOID *)((IMG_UINTPTR_T)psSrcMemInfo->pvLinAddrKM - uPageOffset);
 
-       
-
-
-
+       /*
+               allocate array of SysPAddr to hold SRC allocation page addresses
+       */
        if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                        uPageCount*sizeof(IMG_SYS_PHYADDR),
                                        (IMG_VOID **)&psSysPAddr, IMG_NULL,
@@ -1343,23 +1902,23 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceMemoryKM(PVRSRV_PER_PROCESS_DATA       *psPer
 
        psBuf = psSrcMemInfo->sMemBlk.hBuffer;
 
-       
+       /* get the device node */
        psDeviceNode = psBuf->pMapping->pBMHeap->pBMContext->psDeviceNode;
 
-       
+       /* build a list of physical page addresses */
        sDevVAddr.uiAddr = psSrcMemInfo->sDevVAddr.uiAddr - IMG_CAST_TO_DEVVADDR_UINT(uPageOffset);
        for(i=0; i<uPageCount; i++)
        {
                BM_GetPhysPageAddr(psSrcMemInfo, sDevVAddr, &sDevPAddr);
 
-               
+               /* save the address */
                psSysPAddr[i] = SysDevPAddrToSysPAddr (psDeviceNode->sDevId.eDeviceType, sDevPAddr);
 
-               
+               /* advance the DevVaddr one page */
                sDevVAddr.uiAddr += IMG_CAST_TO_DEVVADDR_UINT(ui32HostPageSize);
        }
 
-       
+       /* allocate the resman map data */
        if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                        sizeof(RESMAN_MAP_DEVICE_MEM_DATA),
                                        (IMG_VOID **)&psMapData, IMG_NULL,
@@ -1401,50 +1960,51 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceMemoryKM(PVRSRV_PER_PROCESS_DATA       *psPer
                goto ErrorExit;
        }
 
-       
+       /* Fill in "Implementation dependant" section of mem info */
        psMemBlock->sDevVirtAddr = BM_HandleToDevVaddr(hBuffer);
        psMemBlock->hOSMemHandle = BM_HandleToOSMemHandle(hBuffer);
 
-       
+       /* Convert from BM_HANDLE to external IMG_HANDLE */
        psMemBlock->hBuffer = (IMG_HANDLE)hBuffer;
 
-       
+       /* Store page list */
        psMemBlock->psIntSysPAddr = psSysPAddr;
 
-       
+       /* patch up the CPU VAddr into the meminfo */
        psMemInfo->pvLinAddrKM = psSrcMemInfo->pvLinAddrKM;
 
-       
+       /* Fill in the public fields of the MEM_INFO structure */
        psMemInfo->sDevVAddr = psMemBlock->sDevVirtAddr;
        psMemInfo->uAllocSize = psSrcMemInfo->uAllocSize;
        psMemInfo->psKernelSyncInfo = psSrcMemInfo->psKernelSyncInfo;
 
-       
+       /* reference the same ksi that the original meminfo referenced */
        if(psMemInfo->psKernelSyncInfo)
        {
-               psMemInfo->psKernelSyncInfo->ui32RefCount++;
+               PVRSRVKernelSyncInfoIncRef(psMemInfo->psKernelSyncInfo, psMemInfo);
        }
 
-       
-
+       /* Clear the Backup buffer pointer as we do not have one at this point.
+          We only allocate this as we are going up/down
+        */
        psMemInfo->pvSysBackupBuffer = IMG_NULL;
 
-       
-       psMemInfo->ui32RefCount++;
+       /* increment our refcount */
+       PVRSRVKernelMemInfoIncRef(psMemInfo);
 
-       
-       psSrcMemInfo->ui32RefCount++;
+       /* increment the src refcount */
+       PVRSRVKernelMemInfoIncRef(psSrcMemInfo);
 
-       
+       /* Tell the buffer manager about the export */
        BM_Export(psSrcMemInfo->sMemBlk.hBuffer);
 
        psMemInfo->memType = PVRSRV_MEMTYPE_MAPPED;
 
-       
+       /* setup the resman map data */
        psMapData->psMemInfo = psMemInfo;
        psMapData->psSrcMemInfo = psSrcMemInfo;
 
-       
+       /* Register Resource */
        psMemInfo->sMemBlk.hResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                                                        RESMAN_TYPE_DEVICEMEM_MAPPING,
                                                                                                        psMapData,
@@ -1455,35 +2015,48 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceMemoryKM(PVRSRV_PER_PROCESS_DATA       *psPer
 
        return PVRSRV_OK;
 
-       
+       /* error handling: */
 
 ErrorExit:
 
        if(psSysPAddr)
        {
-               
+               /* Free the page address list */
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(IMG_SYS_PHYADDR), psSysPAddr, IMG_NULL);
-               
+               /*not nulling shared pointer, holding structure could be not initialized*/
        }
 
        if(psMemInfo)
        {
-               
+               /* Free the page address list */
                OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(PVRSRV_KERNEL_MEM_INFO), psMemInfo, IMG_NULL);
-               
+               /*not nulling shared pointer, holding structure could be not initialized*/
        }
 
        if(psMapData)
        {
-               
+               /* Free the resman map data */
                OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(RESMAN_MAP_DEVICE_MEM_DATA), psMapData, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
        }
 
        return eError;
 }
 
 
+/*!
+******************************************************************************
+       @Function   PVRSRVUnmapDeviceClassMemoryKM
+
+       @Description  unmaps physical pages from devices address space at a specified
+                               Device Virtual Address.
+                               Note: this can only unmap memory mapped by
+                               PVRSRVMapDeviceClassMemoryKM
+
+       @Input      psMemInfo - mem info describing the device virtual address
+                                                                       to unmap RAM from
+       @Return     None
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVUnmapDeviceClassMemoryKM(PVRSRV_KERNEL_MEM_INFO *psMemInfo)
 {
@@ -1496,6 +2069,16 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVUnmapDeviceClassMemoryKM(PVRSRV_KERNEL_MEM_INFO
 }
 
 
+/*!
+******************************************************************************
+       @Function   UnmapDeviceClassMemoryCallBack
+
+       @Description Resman callback to unmap device class memory
+
+       @Input      pvParam - opaque void ptr param
+       @Input      ui32Param - opaque unsigned long param
+       @Return     PVRSRV_ERROR
+******************************************************************************/
 static PVRSRV_ERROR UnmapDeviceClassMemoryCallBack(IMG_PVOID  pvParam,
                                                                                                   IMG_UINT32 ui32Param,
                                                                                                   IMG_BOOL   bDummy)
@@ -1525,10 +2108,28 @@ static PVRSRV_ERROR UnmapDeviceClassMemoryCallBack(IMG_PVOID  pvParam,
 
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_DC_MAPINFO), psDCMapInfo, IMG_NULL);
 
-       return FreeMemCallBackCommon(psMemInfo, ui32Param, IMG_TRUE);
+       return FreeMemCallBackCommon(psMemInfo, ui32Param,
+                                                                PVRSRV_FREE_CALLBACK_ORIGIN_ALLOCATOR);
 }
 
 
+/*!
+******************************************************************************
+       @Function   PVRSRVMapDeviceClassMemoryKM
+
+       @Description  maps physical pages for DeviceClass buffers into a devices
+                               address space at a specified and pre-allocated Device
+                               Virtual Address
+
+       @Input      psPerProc - Per-process data
+       @Input      hDevMemContext - Device memory context
+       @Input      hDeviceClassBuffer - Device Class Buffer (Surface) handle
+       @Input      hDevMemContext - device memory context to which mapping
+                                                                               is made
+       @Output     ppsMemInfo - mem info describing the mapped memory
+       @Output     phOSMapInfo - OS specific mapping information
+       @Return     None
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA *psPerProc,
                                                                                                           IMG_HANDLE                           hDevMemContext,
@@ -1562,7 +2163,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA    *
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* allocate resman storage structure */
        if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                        sizeof(PVRSRV_DC_MAPINFO),
                                        (IMG_VOID **)&psDCMapInfo, IMG_NULL,
@@ -1575,25 +2176,26 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA  *
 
        psDeviceClassBuffer = (PVRSRV_DEVICECLASS_BUFFER*)hDeviceClassBuffer;
 
-       
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+       /*
+               call into external driver to get info so we can map a meminfo
+               Notes:
+               It's expected that third party displays will only support
+               physically contiguous display surfaces.  However, it's possible
+               a given display may have an MMU and therefore support non-contig'
+               display surfaces.
+
+               If surfaces are contiguous, ext driver should return:
+                - a CPU virtual address, or IMG_NULL where the surface is not mapped to CPU
+                - (optional) an OS Mapping handle for KM->UM surface mapping
+                - the size in bytes
+                - a single system physical address
+
+               If surfaces are non-contiguous, ext driver should return:
+                - a CPU virtual address
+                - (optional) an OS Mapping handle for KM->UM surface mapping
+                - the size in bytes (must be multiple of 4kB)
+                - a list of system physical addresses (at 4kB intervals)
+       */
        eError = psDeviceClassBuffer->pfnGetBufferAddr(psDeviceClassBuffer->hExtDevice,
                                                                                                   psDeviceClassBuffer->hExtBuffer,
                                                                                                   &psSysPAddr,
@@ -1608,7 +2210,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA    *
                goto ErrorExitPhase1;
        }
 
-       
+       /* Choose the heap to map to */
        psBMContext = (BM_CONTEXT*)psDeviceClassBuffer->hDevMemContext;
        psDeviceNode = psBMContext->psDeviceNode;
        psDevMemoryInfo = &psDeviceNode->sDevMemoryInfo;
@@ -1619,7 +2221,6 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA    *
                {
                        if(psDeviceMemoryHeap[i].DevMemHeapType == DEVICE_MEMORY_HEAP_PERCONTEXT)
                        {
-                               
                                if (psDeviceMemoryHeap[i].ui32HeapSize > 0)
                                {
                                        hDevMemHeap = BM_CreateHeap(hDevMemContext, &psDeviceMemoryHeap[i]);
@@ -1644,7 +2245,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA    *
                goto ErrorExitPhase1;
        }
 
-       
+       /* Only need lower 12 bits of the cpu addr - don't care what size a void* is */
        ui32Offset = ((IMG_UINTPTR_T)pvCPUVAddr) & (ui32PageSize - 1);
        pvPageAlignedCPUVAddr = (IMG_VOID *)((IMG_UINTPTR_T)pvCPUVAddr - ui32Offset);
 
@@ -1674,32 +2275,40 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA  *
        if (!bBMError)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVMapDeviceClassMemoryKM: BM_Wrap Failed"));
-               
+               /*not nulling pointer, out of scope*/
                eError = PVRSRV_ERROR_BAD_MAPPING;
                goto ErrorExitPhase2;
        }
 
-       
+       /* Fill in "Implementation dependant" section of mem info */
        psMemBlock->sDevVirtAddr = BM_HandleToDevVaddr(hBuffer);
        psMemBlock->hOSMemHandle = BM_HandleToOSMemHandle(hBuffer);
 
-       
+       /* Convert from BM_HANDLE to external IMG_HANDLE */
        psMemBlock->hBuffer = (IMG_HANDLE)hBuffer;
 
-       
-
+       /* patch up the CPU VAddr into the meminfo - use the address from the BM, not the one from the deviceclass
+          api, to ensure user mode mapping is possible
+        */
        psMemInfo->pvLinAddrKM = BM_HandleToCpuVaddr(hBuffer);
 
-       
+       /* Fill in the public fields of the MEM_INFO structure */
        psMemInfo->sDevVAddr = psMemBlock->sDevVirtAddr;
        psMemInfo->uAllocSize = uByteSize;
        psMemInfo->psKernelSyncInfo = psDeviceClassBuffer->psKernelSyncInfo;
 
-       
+       PVR_ASSERT(psMemInfo->psKernelSyncInfo != IMG_NULL);
+       if (psMemInfo->psKernelSyncInfo)
+       {
+               PVRSRVKernelSyncInfoIncRef(psMemInfo->psKernelSyncInfo, psMemInfo);
+       }
 
+       /* Clear the Backup buffer pointer as we do not have one at this point.
+          We only allocate this as we are going up/down
+        */
        psMemInfo->pvSysBackupBuffer = IMG_NULL;
 
-       
+       /* setup DCMapInfo */
        psDCMapInfo->psMemInfo = psMemInfo;
        psDCMapInfo->psDeviceClassBuffer = psDeviceClassBuffer;
 
@@ -1708,7 +2317,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA    *
 
        if(psDCMapInfo->ui32TilingStride > 0)
        {
-               
+               /* try to acquire a tiling range on this device */
                eError = psDeviceNode->pfnAllocMemTilingRange(psDeviceNode,
                                                                                                                psMemInfo,
                                                                                                                psDCMapInfo->ui32TilingStride,
@@ -1721,7 +2330,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA    *
        }
 #endif
 
-       
+       /* Register Resource */
        psMemInfo->sMemBlk.hResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                                                        RESMAN_TYPE_DEVICECLASSMEM_MAPPING,
                                                                                                        psDCMapInfo,
@@ -1729,17 +2338,30 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA  *
                                                                                                        &UnmapDeviceClassMemoryCallBack);
 
        (psDeviceClassBuffer->ui32MemMapRefCount)++;
-       psMemInfo->ui32RefCount++;
+       PVRSRVKernelMemInfoIncRef(psMemInfo);
 
        psMemInfo->memType = PVRSRV_MEMTYPE_DEVICECLASS;
 
-       
+       /* return the meminfo */
        *ppsMemInfo = psMemInfo;
 
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-       
-       PDUMPCOMMENT("Dump display surface");
-       PDUMPMEM(IMG_NULL, psMemInfo, ui32Offset, psMemInfo->uAllocSize, PDUMP_FLAGS_CONTINUOUS, ((BM_BUF*)psMemInfo->sMemBlk.hBuffer)->pMapping);
+       /* If the 3PDD supplies a kernel virtual address, we can PDUMP it */
+       if(psMemInfo->pvLinAddrKM)
+       {
+               /* FIXME:
+                *      Initialise the display surface here when it is mapped into Services.
+                *      Otherwise there is a risk that pdump toolchain will assign previously
+                *      used physical pages, leading to visual artefacts on the unrendered surface
+                *      (e.g. during LLS rendering).
+                *
+                *      A better method is to pdump the allocation from the DC driver, so the
+                *      BM_Wrap pdumps only the virtual memory which better represents the driver
+                *      behaviour.      
+                */
+               PDUMPCOMMENT("Dump display surface");
+               PDUMPMEM(IMG_NULL, psMemInfo, ui32Offset, psMemInfo->uAllocSize, PDUMP_FLAGS_CONTINUOUS, ((BM_BUF*)psMemInfo->sMemBlk.hBuffer)->pMapping);
+       }
 #endif
        return PVRSRV_OK;
 
@@ -1747,10 +2369,16 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVMapDeviceClassMemoryKM(PVRSRV_PER_PROCESS_DATA  *
 ErrorExitPhase3:
        if(psMemInfo)
        {
-               FreeDeviceMem(psMemInfo);
-               
-
+               if (psMemInfo->psKernelSyncInfo)
+               {
+                       PVRSRVKernelSyncInfoDecRef(psMemInfo->psKernelSyncInfo, psMemInfo);
+               }
 
+               FreeDeviceMem(psMemInfo);
+               /*
+                       FreeDeviceMem will free the meminfo so set
+                       it to NULL to avoid double free below
+               */
                psMemInfo = IMG_NULL;
        }
 #endif
@@ -1796,3 +2424,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVChangeDeviceMemoryAttributesKM(IMG_HANDLE hKerne
 }
 
 
+/******************************************************************************
+ End of file (devicemem.c)
+******************************************************************************/
+
index d911b38..1e26047 100644 (file)
@@ -1,30 +1,60 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Resource Handle Manager
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provide resource handle management
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)
+/* See handle.h for a description of the handle API. */
+
+/*
+ * There is no locking here.  It is assumed the code is used in a single
+ * threaded environment.  In particular, it is assumed that the code will
+ * never be called from an interrupt handler.
+ *
+ * The implmentation supports movable handle structures, allowing the address
+ * of a handle structure to change without having to fix up pointers in
+ * any of the handle structures.  For example, the linked list mechanism
+ * used to link subhandles together uses handle array indices rather than
+ * pointers to the structures themselves.
+ */
+
 #include <stddef.h>
 
 #include "services_headers.h"
@@ -47,6 +77,7 @@
 
 #define        INDEX_IS_VALID(psBase, i) ((i) < (psBase)->ui32TotalHandCount)
 
+/* Valid handles are never NULL, but handle array indices are based from 0 */
 #if defined (SUPPORT_SID_INTERFACE)
 #define        INDEX_TO_HANDLE(i) ((IMG_SID)((i) + 1))
 #define        HANDLE_TO_INDEX(h) ((IMG_UINT32)(h) - 1)
 
 #define        MIN(x, y) (((x) < (y)) ? (x) : (y))
 
+/*
+ * Linked list structure.  Used for both the list head and list items.
+ * Array indices, rather than pointers, are used to point to the next and
+ * previous items on the list.
+ */
 struct sHandleList
 {
        IMG_UINT32 ui32Prev;
@@ -128,101 +164,162 @@ enum ePVRSRVInternalHandleFlag
        INTERNAL_HANDLE_FLAG_BATCHED_PARTIALLY_FREE = 0x02,
 };
 
+/* Handle structure */
 struct sHandle
 {
-       
+       /* Handle type */
        PVRSRV_HANDLE_TYPE eType;
 
-       
+       /* Pointer to the data that the handle represents */
        IMG_VOID *pvData;
 
-       
+       /*
+        * When handles are on the free list, the value of the "next index
+        * plus one field" has the following meaning:
+        * zero - next handle is the one that follows this one,
+        * nonzero - the index of the next handle is the value minus one.
+        * This scheme means handle space can be initialised to all zeros.
+        *
+        * When this field is used to link together handles on a list
+        * other than the free list, zero indicates the end of the
+        * list, with nonzero the same as above.
+        */
        IMG_UINT32 ui32NextIndexPlusOne;
 
-       
+       /* Internal flags */
        enum ePVRSRVInternalHandleFlag eInternalFlag;
 
-       
+       /* Flags specified when the handle was allocated */
        PVRSRV_HANDLE_ALLOC_FLAG eFlag;
 
-       
+       /* Index of this handle in the handle array */
        IMG_UINT32 ui32Index;
 
-       
+       /* List head for subhandles of this handle */
        struct sHandleList sChildren;
 
-       
+       /* List entry for sibling subhandles */
        struct sHandleList sSiblings;
 };
 
+/* Handle array index structure.
+ * The handle array is an array of index structures, reallocated as the number of
+ * handles increases.
+ * NOTE: There is one index structure per block of handles.
+ */
 struct sHandleIndex
 {
-       
+       /* Pointer to first handle structure in the block */
        struct sHandle *psHandle;
 
-       
+       /* Block allocation cookie returned from OSAllocMem for the block of handles */
        IMG_HANDLE hBlockAlloc;
 
-       
+       /* Number of free handles in block */
        IMG_UINT32 ui32FreeHandBlockCount;
 };
 
 struct _PVRSRV_HANDLE_BASE_
 {
-       
+       /*  Handle returned from OSAllocMem for handle base allocation */
        IMG_HANDLE hBaseBlockAlloc;
 
-       
+       /* Handle returned from OSAllocMem for handle array allocation */
        IMG_HANDLE hArrayBlockAlloc;
 
-       
+       /* Pointer to array of pointers to handle structures */
        struct sHandleIndex *psHandleArray;
 
-       
+       /*
+        * Pointer to handle hash table.
+        * The hash table is used to do reverse lookups, converting data
+        * pointers to handles.
+        */
        HASH_TABLE *psHashTab;
 
-       
+       /* Number of free handles */
        IMG_UINT32 ui32FreeHandCount;
 
-       
+       /*
+        * If purging is not enabled, this is the array index of first free
+        * handle.
+        * If purging is enabled, this is the index to start searching for
+        * a free handle from.  In this case it is usually zero, unless
+        * the handle array size has been increased due to lack of
+        * handles.
+        */
        IMG_UINT32 ui32FirstFreeIndex;
 
-       
+       /* Maximum handle index, plus one */
        IMG_UINT32 ui32MaxIndexPlusOne;
 
-       
+       /* Total number of handles, free and allocated */
        IMG_UINT32 ui32TotalHandCount;
 
-       
+       /*
+        * Index of the last free index, plus one. Not used if purging
+        * is enabled.
+        */
        IMG_UINT32 ui32LastFreeIndexPlusOne;
 
-       
+       /* Size of current handle batch, or zero if batching not enabled */
        IMG_UINT32 ui32HandBatchSize;
 
-       
+       /* Number of handles prior to start of current batch */
        IMG_UINT32 ui32TotalHandCountPreBatch;
 
-       
+       /* Index of first handle in batch, plus one */
        IMG_UINT32 ui32FirstBatchIndexPlusOne;
 
-       
+       /* Number of handle allocation failures in batch */
        IMG_UINT32 ui32BatchHandAllocFailures;
 
-       
+       /* Purging enabled.
+        * If purging is enabled, the size of the table can be reduced
+        * by removing free space at the end of the table.  To make
+        * purging more likely to succeed, handles are allocated as
+        * far to the front of the table as possible.  The first free
+        * handle is found by a linear search from the start of the table,
+        * and so no free handle list management is done.
+        */
        IMG_BOOL bPurgingEnabled;
 };
 
+/*
+ * The key for the handle hash table is an array of three elements, the
+ * pointer to the resource, the resource type, and the process ID.  The
+ * eHandKey enumeration gives the array indices of the elements making
+ * up the key.
+ */
 enum eHandKey {
        HAND_KEY_DATA = 0,
        HAND_KEY_TYPE,
        HAND_KEY_PARENT,
-       HAND_KEY_LEN                    
+       HAND_KEY_LEN                    /* Must be last item in list */
 };
 
+/*
+ * Kernel handle base structure.  For handles that are not allocated on
+ * behalf of a particular process
+ */
 PVRSRV_HANDLE_BASE *gpsKernelHandleBase = IMG_NULL;
 
+/* HAND_KEY is the type of the hash table key */
 typedef IMG_UINTPTR_T HAND_KEY[HAND_KEY_LEN];
 
+/*!
+******************************************************************************
+
+ @Function     HandleListInit
+
+ @Description  Initialise a linked list structure embedded in a handle
+               structure.
+
+ @Input                ui32Index - index of handle in the handle array
+               psList - pointer to linked list structure
+               hParent - parent handle, or IMG_NULL
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(HandleListInit)
 #endif
@@ -238,6 +335,17 @@ IMG_VOID HandleListInit(IMG_UINT32 ui32Index, struct sHandleList *psList, IMG_HA
        psList->hParent = hParent;
 }
 
+/*!
+******************************************************************************
+
+ @Function     InitParentList
+
+ @Description  Initialise the children list head in a handle structure.
+               The children are the subhandles of this handle.
+
+ @Input                psHandle - pointer to handle structure
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(InitParentList)
 #endif
@@ -249,6 +357,18 @@ IMG_VOID InitParentList(struct sHandle *psHandle)
        HandleListInit(ui32Parent, &psHandle->sChildren, INDEX_TO_HANDLE(ui32Parent));
 }
 
+/*!
+******************************************************************************
+
+ @Function     InitChildEntry
+
+ @Description  Initialise the child list entry in a handle structure.
+               The list entry is used to link together subhandles of
+               a given handle.
+
+ @Input                psHandle - pointer to handle structure
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(InitChildEntry)
 #endif
@@ -258,6 +378,19 @@ IMG_VOID InitChildEntry(struct sHandle *psHandle)
        HandleListInit(HANDLE_PTR_TO_INDEX(psHandle), &psHandle->sSiblings, IMG_NULL);
 }
 
+/*!
+******************************************************************************
+
+ @Function     HandleListIsEmpty
+
+ @Description  Determine whether a given linked list is empty.
+
+ @Input                ui32Index - index of the handle containing the list head
+               psList - pointer to the list head
+
+ @Return       IMG_TRUE if the list is empty, IMG_FALSE if it isn't.
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(HandleListIsEmpty)
 #endif
@@ -273,7 +406,7 @@ IMG_BOOL HandleListIsEmpty(IMG_UINT32 ui32Index, struct sHandleList *psList)
                IMG_BOOL bIsEmpty2;
 
                bIsEmpty2 = (IMG_BOOL)(psList->ui32Prev == ui32Index);
-               PVR_ASSERT(bIsEmpty == bIsEmpty2)
+               PVR_ASSERT(bIsEmpty == bIsEmpty2);
        }
 #endif
 
@@ -281,17 +414,41 @@ IMG_BOOL HandleListIsEmpty(IMG_UINT32 ui32Index, struct sHandleList *psList)
 }
 
 #ifdef DEBUG
+/*!
+******************************************************************************
+
+ @Function     NoChildren
+
+ @Description  Determine whether a handle has any subhandles
+
+ @Input                psHandle - pointer to handle structure
+
+ @Return       IMG_TRUE if the handle has no subhandles, IMG_FALSE if it does.
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(NoChildren)
 #endif
 static INLINE
 IMG_BOOL NoChildren(struct sHandle *psHandle)
 {
-       PVR_ASSERT(psHandle->sChildren.hParent == HANDLE_PTR_TO_HANDLE(psHandle))
+       PVR_ASSERT(psHandle->sChildren.hParent == HANDLE_PTR_TO_HANDLE(psHandle));
 
        return HandleListIsEmpty(HANDLE_PTR_TO_INDEX(psHandle), &psHandle->sChildren);
 }
 
+/*!
+******************************************************************************
+
+ @Function     NoParent
+
+ @Description  Determine whether a handle is a subhandle
+
+ @Input                psHandle - pointer to handle structure
+
+ @Return       IMG_TRUE if the handle is not a subhandle, IMG_FALSE if it is.
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(NoParent)
 #endif
@@ -300,17 +457,29 @@ IMG_BOOL NoParent(struct sHandle *psHandle)
 {
        if (HandleListIsEmpty(HANDLE_PTR_TO_INDEX(psHandle), &psHandle->sSiblings))
        {
-               PVR_ASSERT(psHandle->sSiblings.hParent == IMG_NULL)
+               PVR_ASSERT(psHandle->sSiblings.hParent == IMG_NULL);
 
                return IMG_TRUE;
        }
        else
        {
-               PVR_ASSERT(psHandle->sSiblings.hParent != IMG_NULL)
+               PVR_ASSERT(psHandle->sSiblings.hParent != IMG_NULL);
        }
        return IMG_FALSE;
 }
-#endif 
+#endif /*DEBUG*/
+/*!
+******************************************************************************
+
+ @Function     ParentHandle
+
+ @Description  Determine the parent of a handle
+
+ @Input                psHandle - pointer to handle structure
+
+ @Return       Parent handle, or IMG_NULL if the handle is not a subhandle.
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(ParentHandle)
 #endif
@@ -324,21 +493,49 @@ IMG_HANDLE ParentHandle(struct sHandle *psHandle)
        return psHandle->sSiblings.hParent;
 }
 
+/*
+ * The LIST_PTR_FROM_INDEX_AND_OFFSET macro is used to generate either a
+ * pointer to the subhandle list head, or a pointer to the linked list
+ * structure of an item on a subhandle list.
+ * The list head is itself on the list, but is at a different offset
+ * in the handle structure to the linked list structure for items on
+ * the list.  The two linked list structures are differentiated by
+ * the third parameter, containing the parent index.  The parent field
+ * in the list head structure references the handle structure that contains
+ * it.  For items on the list, the parent field in the linked list structure
+ * references the parent handle, which will be different from the handle
+ * containing the linked list structure.
+ */
 #define        LIST_PTR_FROM_INDEX_AND_OFFSET(psBase, i, p, po, eo) \
                ((struct sHandleList *)((IMG_CHAR *)(INDEX_TO_HANDLE_STRUCT_PTR(psBase, i)) + (((i) == (p)) ? (po) : (eo))))
 
+/*!
+******************************************************************************
+
+ @Function     HandleListInsertBefore
+
+ @Description  Insert a handle before a handle currently on the list.
+
+ @Input                ui32InsIndex - index of handle to be inserted after
+               psIns - pointer to handle structure to be inserted after
+               uiParentOffset - offset to list head struct in handle structure
+               ui32EntryIndex - index of handle to be inserted
+               psEntry - pointer to handle structure of item to be inserted
+               uiEntryOffset - offset of list item struct in handle structure
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(HandleListInsertBefore)
 #endif
 static INLINE
 IMG_VOID HandleListInsertBefore(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32InsIndex, struct sHandleList *psIns, IMG_SIZE_T uiParentOffset, IMG_UINT32 ui32EntryIndex, struct sHandleList *psEntry, IMG_SIZE_T uiEntryOffset, IMG_UINT32 ui32ParentIndex)
 {
-        
+       /* PRQA S 3305 7 */ /*override stricter alignment warning */
        struct sHandleList *psPrevIns = LIST_PTR_FROM_INDEX_AND_OFFSET(psBase, psIns->ui32Prev, ui32ParentIndex, uiParentOffset, uiEntryOffset);
 
-       PVR_ASSERT(psEntry->hParent == IMG_NULL)
-       PVR_ASSERT(ui32InsIndex == psPrevIns->ui32Next)
-       PVR_ASSERT(LIST_PTR_FROM_INDEX_AND_OFFSET(psBase, ui32ParentIndex, ui32ParentIndex, uiParentOffset, uiParentOffset)->hParent == INDEX_TO_HANDLE(ui32ParentIndex))
+       PVR_ASSERT(psEntry->hParent == IMG_NULL);
+       PVR_ASSERT(ui32InsIndex == psPrevIns->ui32Next);
+       PVR_ASSERT(LIST_PTR_FROM_INDEX_AND_OFFSET(psBase, ui32ParentIndex, ui32ParentIndex, uiParentOffset, uiParentOffset)->hParent == INDEX_TO_HANDLE(ui32ParentIndex));
 
        psEntry->ui32Prev = psIns->ui32Prev;
        psIns->ui32Prev = ui32EntryIndex;
@@ -348,6 +545,17 @@ IMG_VOID HandleListInsertBefore(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32InsIn
        psEntry->hParent = INDEX_TO_HANDLE(ui32ParentIndex);
 }
 
+/*!
+******************************************************************************
+
+ @Function     AdoptChild
+
+ @Description  Assign a subhandle to a handle
+
+ @Input                psParent - pointer to handle structure of parent handle
+               psChild - pointer to handle structure of child subhandle
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(AdoptChild)
 #endif
@@ -356,12 +564,25 @@ IMG_VOID AdoptChild(PVRSRV_HANDLE_BASE *psBase, struct sHandle *psParent, struct
 {
        IMG_UINT32 ui32Parent = HANDLE_TO_INDEX(psParent->sChildren.hParent);
 
-       PVR_ASSERT(ui32Parent == HANDLE_PTR_TO_INDEX(psParent))
+       PVR_ASSERT(ui32Parent == HANDLE_PTR_TO_INDEX(psParent));
 
        HandleListInsertBefore(psBase, ui32Parent, &psParent->sChildren, offsetof(struct sHandle, sChildren), HANDLE_PTR_TO_INDEX(psChild), &psChild->sSiblings, offsetof(struct sHandle, sSiblings), ui32Parent);
 
 }
 
+/*!
+******************************************************************************
+
+ @Function     HandleListRemove
+
+ @Description  Remove a handle from a list
+
+ @Input                ui32EntryIndex - index of handle to be removed
+               psEntry - pointer to handle structure of item to be removed
+               uiEntryOffset - offset of list item struct in handle structure
+               uiParentOffset - offset to list head struct in handle structure
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(HandleListRemove)
 #endif
@@ -370,12 +591,15 @@ IMG_VOID HandleListRemove(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32EntryIndex,
 {
        if (!HandleListIsEmpty(ui32EntryIndex, psEntry))
        {
-                
+               /* PRQA S 3305 3 */ /*override stricter alignment warning */
                struct sHandleList *psPrev = LIST_PTR_FROM_INDEX_AND_OFFSET(psBase, psEntry->ui32Prev, HANDLE_TO_INDEX(psEntry->hParent), uiParentOffset, uiEntryOffset);
                struct sHandleList *psNext = LIST_PTR_FROM_INDEX_AND_OFFSET(psBase, psEntry->ui32Next, HANDLE_TO_INDEX(psEntry->hParent), uiParentOffset, uiEntryOffset);
 
-               
-               PVR_ASSERT(psEntry->hParent != IMG_NULL)
+               /*
+                * The list head is on the list, and we don't want to
+                * remove it.
+                */
+               PVR_ASSERT(psEntry->hParent != IMG_NULL);
 
                psPrev->ui32Next = psEntry->ui32Next;
                psNext->ui32Prev = psEntry->ui32Prev;
@@ -384,6 +608,16 @@ IMG_VOID HandleListRemove(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32EntryIndex,
        }
 }
 
+/*!
+******************************************************************************
+
+ @Function     UnlinkFromParent
+
+ @Description  Remove a subhandle from its parents list
+
+ @Input                psHandle - pointer to handle structure of child subhandle
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(UnlinkFromParent)
 #endif
@@ -393,6 +627,19 @@ IMG_VOID UnlinkFromParent(PVRSRV_HANDLE_BASE *psBase, struct sHandle *psHandle)
        HandleListRemove(psBase, HANDLE_PTR_TO_INDEX(psHandle), &psHandle->sSiblings, offsetof(struct sHandle, sSiblings), offsetof(struct sHandle, sChildren));
 }
 
+/*!
+******************************************************************************
+
+ @Function     HandleListIterate
+
+ @Description  Iterate over the items in a list
+
+ @Input                psHead - pointer to list head
+               uiParentOffset - offset to list head struct in handle structure
+               uiEntryOffset - offset of list item struct in handle structure
+               pfnIterFunc - function to be called for each handle in the list
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(HandleListIterate)
 #endif
@@ -402,18 +649,24 @@ PVRSRV_ERROR HandleListIterate(PVRSRV_HANDLE_BASE *psBase, struct sHandleList *p
        IMG_UINT32 ui32Index;
        IMG_UINT32 ui32Parent = HANDLE_TO_INDEX(psHead->hParent);
 
-       PVR_ASSERT(psHead->hParent != IMG_NULL)
+       PVR_ASSERT(psHead->hParent != IMG_NULL);
 
-       
+       /*
+        * Follow the next chain from the list head until we reach
+        * the list head again, which signifies the end of the list.
+        */
        for(ui32Index = psHead->ui32Next; ui32Index != ui32Parent; )
        {
                struct sHandle *psHandle = INDEX_TO_HANDLE_STRUCT_PTR(psBase, ui32Index);
-                
+               /* PRQA S 3305 2 */ /*override stricter alignment warning */
                struct sHandleList *psEntry = LIST_PTR_FROM_INDEX_AND_OFFSET(psBase, ui32Index, ui32Parent, uiParentOffset, uiEntryOffset);
                PVRSRV_ERROR eError;
 
-               PVR_ASSERT(psEntry->hParent == psHead->hParent)
-               
+               PVR_ASSERT(psEntry->hParent == psHead->hParent);
+               /*
+                * Get the next index now, in case the list item is
+                * modified by the iteration function.
+                */
                ui32Index = psEntry->ui32Next;
 
                eError = (*pfnIterFunc)(psBase, psHandle);
@@ -426,6 +679,17 @@ PVRSRV_ERROR HandleListIterate(PVRSRV_HANDLE_BASE *psBase, struct sHandleList *p
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     IterateOverChildren
+
+ @Description  Iterate over the subhandles of a parent handle
+
+ @Input                psParent - pointer to parent handle structure
+               pfnIterFunc - function to be called for each subhandle
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(IterateOverChildren)
 #endif
@@ -435,6 +699,24 @@ PVRSRV_ERROR IterateOverChildren(PVRSRV_HANDLE_BASE *psBase, struct sHandle *psP
         return HandleListIterate(psBase, &psParent->sChildren, offsetof(struct sHandle, sChildren), offsetof(struct sHandle, sSiblings), pfnIterFunc);
 }
 
+/*!
+******************************************************************************
+
+ @Function     GetHandleStructure
+
+ @Description  Get the handle structure for a given handle
+
+ @Input                psBase - pointer to handle base structure
+               ppsHandle - location to return pointer to handle structure
+               hHandle - handle from client
+               eType - handle type or PVRSRV_HANDLE_TYPE_NONE if the
+                       handle type is not to be checked.
+
+ @Output       ppsHandle - points to a pointer to the handle structure
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(GetHandleStructure)
 #endif
@@ -448,7 +730,7 @@ PVRSRV_ERROR GetHandleStructure(PVRSRV_HANDLE_BASE *psBase, struct sHandle **pps
        IMG_UINT32 ui32Index = HANDLE_TO_INDEX(hHandle);
        struct sHandle *psHandle;
 
-       
+       /* Check handle index is in range */
        if (!INDEX_IS_VALID(psBase, ui32Index))
        {
                PVR_DPF((PVR_DBG_ERROR, "GetHandleStructure: Handle index out of range (%u >= %u)", ui32Index, psBase->ui32TotalHandCount));
@@ -468,7 +750,10 @@ PVRSRV_ERROR GetHandleStructure(PVRSRV_HANDLE_BASE *psBase, struct sHandle **pps
                return PVRSRV_ERROR_HANDLE_NOT_ALLOCATED;
        }
 
-       
+       /*
+        * Unless PVRSRV_HANDLE_TYPE_NONE was passed in to this function,
+        * check handle is of the correct type.
+        */
        if (eType != PVRSRV_HANDLE_TYPE_NONE && eType != psHandle->eType)
        {
                PVR_DPF((PVR_DBG_ERROR, "GetHandleStructure: Handle type mismatch (%d != %d)", eType, psHandle->eType));
@@ -478,12 +763,26 @@ PVRSRV_ERROR GetHandleStructure(PVRSRV_HANDLE_BASE *psBase, struct sHandle **pps
                return PVRSRV_ERROR_HANDLE_TYPE_MISMATCH;
        }
 
-       
+       /* Return the handle structure */
        *ppsHandle = psHandle;
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     ParentIfPrivate
+
+ @Description  Return the parent handle if the handle was allocated
+               with PVRSRV_HANDLE_ALLOC_FLAG_PRIVATE, else return
+               IMG_NULL
+
+ @Input                psHandle - pointer to handle
+
+ @Return       Parent handle, or IMG_NULL
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(ParentIfPrivate)
 #endif
@@ -498,6 +797,19 @@ IMG_HANDLE ParentIfPrivate(struct sHandle *psHandle)
                        ParentHandle(psHandle) : IMG_NULL;
 }
 
+/*!
+******************************************************************************
+
+ @Function     InitKey
+
+ @Description  Initialise a hash table key for the current process
+
+ @Input                psBase - pointer to handle base structure
+               aKey - pointer to key
+               pvData - pointer to the resource the handle represents
+               eType - type of resource
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(InitKey)
 #endif
@@ -515,6 +827,21 @@ IMG_VOID InitKey(HAND_KEY aKey, PVRSRV_HANDLE_BASE *psBase, IMG_VOID *pvData, PV
        aKey[HAND_KEY_PARENT] = (IMG_UINTPTR_T)hParent;
 }
 
+/*!
+******************************************************************************
+
+ @Function     ReallocHandleArray
+
+ @Description  Reallocate the handle array
+
+ @Input                psBase - handle base.
+               phBlockAlloc - pointer to block allocation handle.
+               ui32NewCount - new handle count
+               ui32OldCount - old handle count
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 static
 PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCount)
 {
@@ -541,15 +868,15 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
        if (((ui32OldCount % HANDLE_BLOCK_SIZE) != 0) ||
                ((ui32NewCount % HANDLE_BLOCK_SIZE) != 0))
        {
-               PVR_ASSERT((ui32OldCount % HANDLE_BLOCK_SIZE) == 0)
-               PVR_ASSERT((ui32NewCount % HANDLE_BLOCK_SIZE) == 0)
+               PVR_ASSERT((ui32OldCount % HANDLE_BLOCK_SIZE) == 0);
+               PVR_ASSERT((ui32NewCount % HANDLE_BLOCK_SIZE) == 0);
 
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
        if (ui32NewCount != 0)
        {
-               
+               /* Allocate new handle array */
                eError = OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                        HANDLE_ARRAY_SIZE(ui32NewCount) * sizeof(struct sHandleIndex),
                        (IMG_VOID **)&psNewArray,
@@ -568,7 +895,10 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
                }
        }
 
-       
+       /*
+        * If the new handle array is smaller than the old one, free
+        * unused handle structures
+        */
        for(ui32Index = ui32NewCount; ui32Index < ui32OldCount; ui32Index += HANDLE_BLOCK_SIZE)
        {
                struct sHandleIndex *psIndex = INDEX_TO_INDEX_STRUCT_PTR(psOldArray, ui32Index);
@@ -583,10 +913,13 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
                }
        }
 
-       
+       /*
+        * If the new handle array is bigger than the old one, allocate
+        * new handle structures
+        */
        for(ui32Index = ui32OldCount; ui32Index < ui32NewCount; ui32Index += HANDLE_BLOCK_SIZE)
        {
-                
+               /* PRQA S 0505 1 */ /* psNewArray is never NULL, see assert earlier */
                struct sHandleIndex *psIndex = INDEX_TO_INDEX_STRUCT_PTR(psNewArray, ui32Index);
 
                eError = OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
@@ -624,7 +957,7 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
        }
 
 #ifdef DEBUG_MAX_HANDLE_COUNT
-       
+       /* Force handle failure to test error exit code */
        if (ui32NewCount > DEBUG_MAX_HANDLE_COUNT)
        {
                PVR_DPF((PVR_DBG_ERROR, "ReallocHandleArray: Max handle count (%u) reached", DEBUG_MAX_HANDLE_COUNT));
@@ -635,7 +968,7 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
 
        if (psOldArray != IMG_NULL)
        {
-               
+               /* Free old handle array */
                eError = OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
                        HANDLE_ARRAY_SIZE(ui32OldCount) * sizeof(struct sHandleIndex),
                        psOldArray,
@@ -652,16 +985,21 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
 
        if (ui32NewCount > ui32OldCount)
        {
-               
-               PVR_ASSERT(psBase->ui32FreeHandCount + (ui32NewCount - ui32OldCount) > psBase->ui32FreeHandCount)
+               /* Check for wraparound */
+               PVR_ASSERT(psBase->ui32FreeHandCount + (ui32NewCount - ui32OldCount) > psBase->ui32FreeHandCount);
 
-                
+               /* PRQA S 3382 1 */ /* ui32NewCount always > ui32OldCount */
                psBase->ui32FreeHandCount += (ui32NewCount - ui32OldCount);
 
-               
+               /*
+                * If purging is enabled, there is no free handle list
+                * management, but as an optimization, when allocating
+                * new handles, we use ui32FirstFreeIndex to point to
+                * the first handle in a newly allocated block.
+                */
                if (psBase->ui32FirstFreeIndex == 0)
                {
-                       PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne == 0)
+                       PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne == 0);
 
                        psBase->ui32FirstFreeIndex = ui32OldCount;
                }
@@ -669,8 +1007,8 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
                {
                        if (!psBase->bPurgingEnabled)
                        {
-                               PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne != 0)
-                               PVR_ASSERT(INDEX_TO_HANDLE_STRUCT_PTR(psBase, psBase->ui32LastFreeIndexPlusOne - 1)->ui32NextIndexPlusOne == 0)
+                               PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne != 0);
+                               PVR_ASSERT(INDEX_TO_HANDLE_STRUCT_PTR(psBase, psBase->ui32LastFreeIndexPlusOne - 1)->ui32NextIndexPlusOne == 0);
 
                                INDEX_TO_HANDLE_STRUCT_PTR(psBase, psBase->ui32LastFreeIndexPlusOne - 1)->ui32NextIndexPlusOne = ui32OldCount + 1;
                        }
@@ -683,11 +1021,11 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
        }
        else
        {
-               PVR_ASSERT(ui32NewCount == 0 || psBase->bPurgingEnabled)
-               PVR_ASSERT(ui32NewCount == 0 || psBase->ui32FirstFreeIndex <= ui32NewCount)
-               PVR_ASSERT(psBase->ui32FreeHandCount - (ui32OldCount - ui32NewCount) < psBase->ui32FreeHandCount)
+               PVR_ASSERT(ui32NewCount == 0 || psBase->bPurgingEnabled);
+               PVR_ASSERT(ui32NewCount == 0 || psBase->ui32FirstFreeIndex <= ui32NewCount);
+               PVR_ASSERT(psBase->ui32FreeHandCount - (ui32OldCount - ui32NewCount) < psBase->ui32FreeHandCount);
 
-                
+               /* PRQA S 3382 1 */ /* ui32OldCount always >= ui32NewCount */
                psBase->ui32FreeHandCount -= (ui32OldCount - ui32NewCount);
 
                if (ui32NewCount == 0)
@@ -697,16 +1035,16 @@ PVRSRV_ERROR ReallocHandleArray(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32NewCo
                }
        }
 
-       PVR_ASSERT(psBase->ui32FirstFreeIndex <= psBase->ui32TotalHandCount)
+       PVR_ASSERT(psBase->ui32FirstFreeIndex <= psBase->ui32TotalHandCount);
 
        return PVRSRV_OK;
 
 error:
-       PVR_ASSERT(eReturn != PVRSRV_OK)
+       PVR_ASSERT(eReturn != PVRSRV_OK);
 
        if (psNewArray != IMG_NULL)
        {
-               
+               /* Free any new handle structures that were allocated */
                for(ui32Index = ui32OldCount; ui32Index < ui32NewCount; ui32Index += HANDLE_BLOCK_SIZE)
                {
                        struct sHandleIndex *psIndex = INDEX_TO_INDEX_STRUCT_PTR(psNewArray, ui32Index);
@@ -723,7 +1061,7 @@ error:
                        }
                }
 
-               
+               /* Free new handle array */
                eError = OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
                        HANDLE_ARRAY_SIZE(ui32NewCount) * sizeof(struct sHandleIndex),
                        psNewArray,
@@ -737,18 +1075,52 @@ error:
        return eReturn;
 }
 
+/*!
+******************************************************************************
+
+ @Function     FreeHandleArray
+
+ @Description  Frees the handle array.
+               The memory containing the array of handle structure
+               pointers is deallocated.
+
+ @Input                psBase - pointer to handle base structure
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 static PVRSRV_ERROR FreeHandleArray(PVRSRV_HANDLE_BASE *psBase)
 {
        return ReallocHandleArray(psBase, 0);
 }
 
+/*!
+******************************************************************************
+
+ @Function     FreeHandle
+
+ @Description  Free a handle structure.
+
+ @Input                psBase - pointer to handle base structure
+               psHandle - pointer to handle structure
+
+ @Return       PVRSRV_OK or PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR FreeHandle(PVRSRV_HANDLE_BASE *psBase, struct sHandle *psHandle)
 {
        HAND_KEY aKey;
        IMG_UINT32 ui32Index = HANDLE_PTR_TO_INDEX(psHandle);
        PVRSRV_ERROR eError;
 
-       
+       /*
+        * If a handle allocated in batch mode is freed whilst still
+        * in batch mode, the type is set to PVRSRV_HANDLE_TYPE_NONE further
+        * down, to indicate the handle will not be used, but not actually
+        * freed.  The Free is completed when this function is called a
+        * second time as part of the batch commit or release.
+        */
+
        InitKey(aKey, psBase, psHandle->pvData, psHandle->eType, ParentIfPrivate(psHandle));
 
        if (!TEST_ALLOC_FLAG(psHandle, PVRSRV_HANDLE_ALLOC_FLAG_MULTI) && !BATCHED_HANDLE_PARTIALLY_FREE(psHandle))
@@ -762,15 +1134,15 @@ static PVRSRV_ERROR FreeHandle(PVRSRV_HANDLE_BASE *psBase, struct sHandle *psHan
 
 #endif
 
-               PVR_ASSERT(hHandle != IMG_NULL)
-               PVR_ASSERT(hHandle == INDEX_TO_HANDLE(ui32Index))
+               PVR_ASSERT(hHandle != IMG_NULL);
+               PVR_ASSERT(hHandle == INDEX_TO_HANDLE(ui32Index));
                PVR_UNREFERENCED_PARAMETER(hHandle);
        }
 
-       
+       /* Unlink handle from parent */
        UnlinkFromParent(psBase, psHandle);
 
-       
+       /* Free children */
        eError = IterateOverChildren(psBase, psHandle, FreeHandle);
        if (eError != PVRSRV_OK)
        {
@@ -778,45 +1150,54 @@ static PVRSRV_ERROR FreeHandle(PVRSRV_HANDLE_BASE *psBase, struct sHandle *psHan
                return eError;
        }
 
-       
+       /*
+        * Clear the type here, so that a handle can no longer be looked
+        * up if it is only partially freed.
+        */
        psHandle->eType = PVRSRV_HANDLE_TYPE_NONE;
 
        if (BATCHED_HANDLE(psHandle) && !BATCHED_HANDLE_PARTIALLY_FREE(psHandle))
        {
-                
+               /* PRQA S 1474,4130 1 */ /* ignore warnings about enum types being modified */
         SET_BATCHED_HANDLE_PARTIALLY_FREE(psHandle);
-               
+               /*
+                * If the handle was allocated in batch mode, delay the free
+                * until the batch commit or release.
+                */
                return PVRSRV_OK;
        }
 
-       
+       /* No free list management if purging is enabled */
        if (!psBase->bPurgingEnabled)
        {
                if (psBase->ui32FreeHandCount == 0)
                {
-                       PVR_ASSERT(psBase->ui32FirstFreeIndex == 0)
-                       PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne == 0)
+                       PVR_ASSERT(psBase->ui32FirstFreeIndex == 0);
+                       PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne == 0);
 
                        psBase->ui32FirstFreeIndex =  ui32Index;
                }
                else
                {
-                       
-                       PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne != 0)
-                       PVR_ASSERT(INDEX_TO_HANDLE_STRUCT_PTR(psBase, psBase->ui32LastFreeIndexPlusOne - 1)->ui32NextIndexPlusOne == 0)
+                       /*
+                        * Put the handle pointer on the end of the the free
+                        * handle pointer linked list.
+                        */
+                       PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne != 0);
+                       PVR_ASSERT(INDEX_TO_HANDLE_STRUCT_PTR(psBase, psBase->ui32LastFreeIndexPlusOne - 1)->ui32NextIndexPlusOne == 0);
                        INDEX_TO_HANDLE_STRUCT_PTR(psBase, psBase->ui32LastFreeIndexPlusOne - 1)->ui32NextIndexPlusOne =  ui32Index + 1;
                }
 
-               PVR_ASSERT(psHandle->ui32NextIndexPlusOne == 0)
+               PVR_ASSERT(psHandle->ui32NextIndexPlusOne == 0);
 
-               
+               /* Update the end of the free handle linked list */
                psBase->ui32LastFreeIndexPlusOne = ui32Index + 1;
        }
 
        psBase->ui32FreeHandCount++;
        INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32Index)++;
 
-       PVR_ASSERT(INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32Index)<= HANDLE_BLOCK_SIZE)
+       PVR_ASSERT(INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32Index)<= HANDLE_BLOCK_SIZE);
 
 #ifdef DEBUG
        {
@@ -828,13 +1209,25 @@ static PVRSRV_ERROR FreeHandle(PVRSRV_HANDLE_BASE *psBase, struct sHandle *psHan
                        ui32FreeHandCount += INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32BlockedIndex);
                }
 
-               PVR_ASSERT(ui32FreeHandCount == psBase->ui32FreeHandCount)
+               PVR_ASSERT(ui32FreeHandCount == psBase->ui32FreeHandCount);
        }
 #endif
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     FreeAllHandles
+
+ @Description  Free all handles for a given handle base
+
+ @Input                psBase - pointer to handle base structure
+
+ @Return       PVRSRV_OK or PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR FreeAllHandles(PVRSRV_HANDLE_BASE *psBase)
 {
        IMG_UINT32 i;
@@ -860,7 +1253,7 @@ static PVRSRV_ERROR FreeAllHandles(PVRSRV_HANDLE_BASE *psBase)
                                break;
                        }
 
-                       
+                       /* Break out of loop if all the handles free */
                        if (psBase->ui32FreeHandCount == psBase->ui32TotalHandCount)
                        {
                                break;
@@ -871,6 +1264,18 @@ static PVRSRV_ERROR FreeAllHandles(PVRSRV_HANDLE_BASE *psBase)
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     FreeHandleBase
+
+ @Description  Free a handle base.
+
+ @Input                psHandleBase - pointer to handle base
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 static PVRSRV_ERROR FreeHandleBase(PVRSRV_HANDLE_BASE *psBase)
 {
        PVRSRV_ERROR eError;
@@ -881,7 +1286,7 @@ static PVRSRV_ERROR FreeHandleBase(PVRSRV_HANDLE_BASE *psBase)
                PVRSRVReleaseHandleBatch(psBase);
        }
 
-       
+       /* Free the handle array */
        eError = FreeAllHandles(psBase);
        if (eError != PVRSRV_OK)
        {
@@ -889,7 +1294,7 @@ static PVRSRV_ERROR FreeHandleBase(PVRSRV_HANDLE_BASE *psBase)
                return eError;
        }
 
-       
+       /* Free the handle array */
        eError = FreeHandleArray(psBase);
        if (eError != PVRSRV_OK)
        {
@@ -899,7 +1304,7 @@ static PVRSRV_ERROR FreeHandleBase(PVRSRV_HANDLE_BASE *psBase)
 
        if (psBase->psHashTab != IMG_NULL)
        {
-               
+               /* Free the hash table */
                HASH_Delete(psBase->psHashTab);
        }
 
@@ -916,6 +1321,20 @@ static PVRSRV_ERROR FreeHandleBase(PVRSRV_HANDLE_BASE *psBase)
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     FindHandle
+
+ @Description  Find handle corresponding to a resource pointer
+
+ @Input                psBase - pointer to handle base structure
+               pvData - pointer to resource to be associated with the handle
+               eType - the type of resource
+
+ @Return       the handle, or IMG_NULL if not found
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(FindHandle)
 #endif
@@ -928,7 +1347,7 @@ IMG_HANDLE FindHandle(PVRSRV_HANDLE_BASE *psBase, IMG_VOID *pvData, PVRSRV_HANDL
 {
        HAND_KEY aKey;
 
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 
        InitKey(aKey, psBase, pvData, eType, hParent);
 
@@ -939,16 +1358,30 @@ IMG_HANDLE FindHandle(PVRSRV_HANDLE_BASE *psBase, IMG_VOID *pvData, PVRSRV_HANDL
 #endif
 }
 
+/*!
+******************************************************************************
+
+ @Function     IncreaseHandleArraySize
+
+ @Description  Allocate some more free handles
+
+ @Input                psBase - pointer to handle base structure
+               ui32Delta - number of new handles required
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 static PVRSRV_ERROR IncreaseHandleArraySize(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32Delta)
 {
        PVRSRV_ERROR eError;
        IMG_UINT32 ui32DeltaAdjusted = ROUND_UP_TO_MULTIPLE_OF_BLOCK_SIZE(ui32Delta);
        IMG_UINT32 ui32NewTotalHandCount = psBase->ui32TotalHandCount + ui32DeltaAdjusted;
-;
 
-       PVR_ASSERT(ui32Delta != 0)
+       PVR_ASSERT(ui32Delta != 0);
 
-       
+       /*
+        * Check new count against max handle index, and check for wrap around.
+        */
        if (ui32NewTotalHandCount > psBase->ui32MaxIndexPlusOne || ui32NewTotalHandCount <= psBase->ui32TotalHandCount)
        {
                ui32NewTotalHandCount = psBase->ui32MaxIndexPlusOne;
@@ -962,9 +1395,9 @@ static PVRSRV_ERROR IncreaseHandleArraySize(PVRSRV_HANDLE_BASE *psBase, IMG_UINT
                }
        }
 
-       PVR_ASSERT(ui32DeltaAdjusted >= ui32Delta)
+       PVR_ASSERT(ui32DeltaAdjusted >= ui32Delta);
 
-       
+       /* Realloc handle pointer array */
        eError = ReallocHandleArray(psBase, ui32NewTotalHandCount);
        if (eError != PVRSRV_OK)
        {
@@ -975,6 +1408,19 @@ static PVRSRV_ERROR IncreaseHandleArraySize(PVRSRV_HANDLE_BASE *psBase, IMG_UINT
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     EnsureFreeHandles
+
+ @Description  Ensure there are enough free handles
+
+ @Input                psBase - pointer to handle base structure
+               ui32Free - number of free handles required
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 static PVRSRV_ERROR EnsureFreeHandles(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32Free)
 {
        PVRSRV_ERROR eError;
@@ -994,6 +1440,23 @@ static PVRSRV_ERROR EnsureFreeHandles(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui3
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     AllocHandle
+
+ @Description  Allocate a new handle
+
+ @Input                phHandle - location for new handle
+               pvData - pointer to resource to be associated with the handle
+               eType - the type of resource
+               hParent - parent handle or IMG_NULL
+
+ @Output       phHandle - points to new handle
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 static PVRSRV_ERROR AllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_SID *phHandle, IMG_VOID *pvData, PVRSRV_HANDLE_TYPE eType, PVRSRV_HANDLE_ALLOC_FLAG eFlag, IMG_SID hParent)
 #else
@@ -1010,15 +1473,15 @@ static PVRSRV_ERROR AllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle
        HAND_KEY aKey;
        PVRSRV_ERROR eError;
 
-       
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
-       PVR_ASSERT(psBase != IMG_NULL)
-       PVR_ASSERT(psBase->psHashTab != IMG_NULL)
+       /* PVRSRV_HANDLE_TYPE_NONE is reserved for internal use */
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
+       PVR_ASSERT(psBase != IMG_NULL);
+       PVR_ASSERT(psBase->psHashTab != IMG_NULL);
 
        if (!TEST_FLAG(eFlag, PVRSRV_HANDLE_ALLOC_FLAG_MULTI))
        {
-               
-               PVR_ASSERT(FindHandle(psBase, pvData, eType, hParent) == IMG_NULL)
+               /* Handle must not already exist */
+               PVR_ASSERT(FindHandle(psBase, pvData, eType, hParent) == IMG_NULL);
        }
 
        if (psBase->ui32FreeHandCount == 0 && HANDLES_BATCHED(psBase))
@@ -1026,30 +1489,41 @@ static PVRSRV_ERROR AllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle
                 PVR_DPF((PVR_DBG_WARNING, "AllocHandle: Handle batch size (%u) was too small, allocating additional space", psBase->ui32HandBatchSize)); 
        }
 
-       
+       /* Ensure there is a free handle */
        eError = EnsureFreeHandles(psBase, 1);
        if (eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR, "AllocHandle: EnsureFreeHandles failed (%d)", eError));
                return eError;
        }
-       PVR_ASSERT(psBase->ui32FreeHandCount != 0)
+       PVR_ASSERT(psBase->ui32FreeHandCount != 0);
 
        if (!psBase->bPurgingEnabled)
        {
-               
+               /* Array index of first free handle */
                ui32NewIndex = psBase->ui32FirstFreeIndex;
 
-               
+               /* Get handle array entry */
                psNewHandle = INDEX_TO_HANDLE_STRUCT_PTR(psBase, ui32NewIndex);
        }
        else
        {
                IMG_UINT32 ui32BlockedIndex;
 
-               
-               
-               PVR_ASSERT((psBase->ui32FirstFreeIndex % HANDLE_BLOCK_SIZE) == 0)
+               /*
+                * If purging is enabled, we always try to allocate handles
+                * at the front of the array, to increase the chances that
+                * the size of the handle array can be reduced by a purge.
+                * No linked list of free handles is kept; we search for
+                * free handles as required.
+                */
+
+               /*
+                * ui32FirstFreeIndex should only be set when a new batch of
+                * handle structures is allocated, and should always be a
+                * multiple of the block size.
+                */
+               PVR_ASSERT((psBase->ui32FirstFreeIndex % HANDLE_BLOCK_SIZE) == 0);
 
                for (ui32BlockedIndex = ROUND_DOWN_TO_MULTIPLE_OF_BLOCK_SIZE(psBase->ui32FirstFreeIndex); ui32BlockedIndex < psBase->ui32TotalHandCount; ui32BlockedIndex += HANDLE_BLOCK_SIZE)
                {
@@ -1070,20 +1544,24 @@ static PVRSRV_ERROR AllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle
                        }
                }
                psBase->ui32FirstFreeIndex = 0;
-               PVR_ASSERT(ui32NewIndex < psBase->ui32TotalHandCount)
+               PVR_ASSERT(ui32NewIndex < psBase->ui32TotalHandCount);
        }
-       PVR_ASSERT(psNewHandle != IMG_NULL)
+       PVR_ASSERT(psNewHandle != IMG_NULL);
 
-       
+       /* Handle to be returned to client */
        hHandle = INDEX_TO_HANDLE(ui32NewIndex);
 
-       
+       /*
+        * If a data pointer can be associated with multiple handles, we
+        * don't put the handle in the hash table, as the data pointer
+        * may not map to a unique handle
+        */
        if (!TEST_FLAG(eFlag, PVRSRV_HANDLE_ALLOC_FLAG_MULTI))
        {
-               
+               /* Initialise hash key */
                InitKey(aKey, psBase, pvData, eType, hParent);
 
-               
+               /* Put the new handle in the hash table */
                if (!HASH_Insert_Extended(psBase->psHashTab, aKey, (IMG_UINTPTR_T)hHandle))
                {
                        PVR_DPF((PVR_DBG_ERROR, "AllocHandle: Couldn't add handle to hash table"));
@@ -1094,36 +1572,44 @@ static PVRSRV_ERROR AllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle
 
        psBase->ui32FreeHandCount--;
 
-       PVR_ASSERT(INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32NewIndex) <= HANDLE_BLOCK_SIZE)
-       PVR_ASSERT(INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32NewIndex) > 0)
+       PVR_ASSERT(INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32NewIndex) <= HANDLE_BLOCK_SIZE);
+       PVR_ASSERT(INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32NewIndex) > 0);
 
        INDEX_TO_FREE_HAND_BLOCK_COUNT(psBase, ui32NewIndex)--;
 
-       
+       /* No free list management if purging is enabled */
        if (!psBase->bPurgingEnabled)
        {
-               
+               /* Check whether the last free handle has been allocated */
                if (psBase->ui32FreeHandCount == 0)
                {
-                       PVR_ASSERT(psBase->ui32FirstFreeIndex == ui32NewIndex)
-                       PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne == (ui32NewIndex + 1))
+                       PVR_ASSERT(psBase->ui32FirstFreeIndex == ui32NewIndex);
+                       PVR_ASSERT(psBase->ui32LastFreeIndexPlusOne == (ui32NewIndex + 1));
 
                        psBase->ui32LastFreeIndexPlusOne = 0;
                        psBase->ui32FirstFreeIndex = 0;
                }
                else
                {
-                       
+                       /*
+                        * Update the first free handle index.
+                        * If the "next free index plus one" field in the new
+                        * handle structure is zero, the next free index is
+                        * the index of the new handle plus one.  This
+                        * convention has been adopted to simplify the
+                        * initialisation of freshly allocated handle
+                        * space.
+                        */
                        psBase->ui32FirstFreeIndex = (psNewHandle->ui32NextIndexPlusOne == 0) ?
                                ui32NewIndex + 1 :
                                psNewHandle->ui32NextIndexPlusOne - 1;
                }
        }
 
-       
-       PVR_ASSERT(psNewHandle->ui32Index == ui32NewIndex)
+       /* Initialise the newly allocated handle */
+       PVR_ASSERT(psNewHandle->ui32Index == ui32NewIndex);
 
-        
+       /* PRQA S 0505 1 */ /* psNewHandle is never NULL, see assert earlier */
        psNewHandle->eType = eType;
        psNewHandle->pvData = pvData;
        psNewHandle->eInternalFlag = INTERNAL_HANDLE_FLAG_NONE;
@@ -1131,22 +1617,22 @@ static PVRSRV_ERROR AllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle
 
        InitParentList(psNewHandle);
 #if defined(DEBUG)
-       PVR_ASSERT(NoChildren(psNewHandle))
+       PVR_ASSERT(NoChildren(psNewHandle));
 #endif
 
        InitChildEntry(psNewHandle);
 #if defined(DEBUG)
-       PVR_ASSERT(NoParent(psNewHandle))
+       PVR_ASSERT(NoParent(psNewHandle));
 #endif
 
        if (HANDLES_BATCHED(psBase))
        {
-               
+               /* Add handle to batch list */
                psNewHandle->ui32NextIndexPlusOne = psBase->ui32FirstBatchIndexPlusOne;
 
                psBase->ui32FirstBatchIndexPlusOne = ui32NewIndex + 1;
 
-                
+               /* PRQA S 1474 1 */ /* ignore warnings about enum types being modified */
                SET_BATCHED_HANDLE(psNewHandle);
        }
        else
@@ -1154,12 +1640,28 @@ static PVRSRV_ERROR AllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle
                psNewHandle->ui32NextIndexPlusOne = 0;
        }
 
-       
+       /* Return the new handle to the client */
        *phHandle = hHandle;
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVAllocHandle
+
+ @Description  Allocate a handle
+
+ @Input                phHandle - location for new handle
+               pvData - pointer to resource to be associated with the handle
+               eType - the type of resource
+
+ @Output       phHandle - points to new handle
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVAllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_SID *phHandle, IMG_VOID *pvData, PVRSRV_HANDLE_TYPE eType, PVRSRV_HANDLE_ALLOC_FLAG eFlag)
 #else
@@ -1181,16 +1683,19 @@ PVRSRV_ERROR PVRSRVAllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle,
 
        if (HANDLES_BATCHED(psBase))
        {
-               
+               /*
+                * Increment the counter in case of failure.  It will be
+                * decremented on success.
+                */
                psBase->ui32BatchHandAllocFailures++;
        }
 
-       
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       /* PVRSRV_HANDLE_TYPE_NONE is reserved for internal use */
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 
        if (!TEST_FLAG(eFlag, PVRSRV_HANDLE_ALLOC_FLAG_MULTI))
        {
-               
+               /* See if there is already a handle for this data pointer */
                hHandle = FindHandle(psBase, pvData, eType, IMG_NULL);
 #if defined (SUPPORT_SID_INTERFACE)
                if (hHandle != 0)
@@ -1207,7 +1712,11 @@ PVRSRV_ERROR PVRSRVAllocHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle,
                                return eError;
                        }
 
-                       
+                       /*
+                        * If the client is willing to share a handle, and the
+                        * existing handle is marked as shareable, return the
+                        * existing handle.
+                        */
                        if (TEST_FLAG(psHandle->eFlag & eFlag, PVRSRV_HANDLE_ALLOC_FLAG_SHARED))
                        {
                                *phHandle = hHandle;
@@ -1233,6 +1742,23 @@ exit_ok:
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVAllocSubHandle
+
+ @Description  Allocate a subhandle
+
+ @Input                phHandle - location for new subhandle
+               pvData - pointer to resource to be associated with the subhandle
+               eType - the type of resource
+               hParent - parent handle
+
+ @Output       phHandle - points to new subhandle
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVAllocSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_SID *phHandle, IMG_VOID *pvData, PVRSRV_HANDLE_TYPE eType, PVRSRV_HANDLE_ALLOC_FLAG eFlag, IMG_SID hParent)
 #else
@@ -1256,17 +1782,20 @@ PVRSRV_ERROR PVRSRVAllocSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHand
 
        if (HANDLES_BATCHED(psBase))
        {
-               
+               /*
+                * Increment the counter in case of failure.  It will be
+                * decremented on success.
+                */
                psBase->ui32BatchHandAllocFailures++;
        }
 
-       
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       /* PVRSRV_HANDLE_TYPE_NONE is reserved for internal use */
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 
        hParentKey = TEST_FLAG(eFlag, PVRSRV_HANDLE_ALLOC_FLAG_PRIVATE) ?
                        hParent : IMG_NULL;
 
-       
+       /* Lookup the parent handle */
        eError = GetHandleStructure(psBase, &psPHand, hParent, PVRSRV_HANDLE_TYPE_NONE);
        if (eError != PVRSRV_OK)
        {
@@ -1275,7 +1804,7 @@ PVRSRV_ERROR PVRSRVAllocSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHand
 
        if (!TEST_FLAG(eFlag, PVRSRV_HANDLE_ALLOC_FLAG_MULTI))
        {
-               
+               /* See if there is already a handle for this data pointer */
                hHandle = FindHandle(psBase, pvData, eType, hParentKey);
 #if defined (SUPPORT_SID_INTERFACE)
                if (hHandle != 0)
@@ -1293,9 +1822,14 @@ PVRSRV_ERROR PVRSRVAllocSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHand
                                return eErr;
                        }
 
-                       PVR_ASSERT(hParentKey != IMG_NULL && ParentHandle(HANDLE_TO_HANDLE_STRUCT_PTR(psBase, hHandle)) == hParent)
+                       PVR_ASSERT(hParentKey != IMG_NULL && ParentHandle(HANDLE_TO_HANDLE_STRUCT_PTR(psBase, hHandle)) == hParent);
 
-                       
+                       /*
+                        * If the client is willing to share a handle, the
+                        * existing handle is marked as shareable, and the
+                        * existing handle has the same parent, return the
+                        * existing handle.
+                        */
                        if (TEST_FLAG(psCHandle->eFlag & eFlag, PVRSRV_HANDLE_ALLOC_FLAG_SHARED) && ParentHandle(HANDLE_TO_HANDLE_STRUCT_PTR(psBase, hHandle)) == hParent)
                        {
                                *phHandle = hHandle;
@@ -1314,7 +1848,11 @@ PVRSRV_ERROR PVRSRVAllocSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHand
                return eError;
        }
 
-       
+       /*
+        * Get the parent handle structure again, in case the handle
+        * structure has moved (depending on the implementation
+        * of AllocHandle).
+        */
        psPHand = HANDLE_TO_HANDLE_STRUCT_PTR(psBase, hParent);
 
        psCHand = HANDLE_TO_HANDLE_STRUCT_PTR(psBase, hHandle);
@@ -1332,6 +1870,22 @@ exit_ok:
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVFindHandle
+
+ @Description  Find handle corresponding to a resource pointer
+
+ @Input                phHandle - location for returned handle
+               pvData - pointer to resource to be associated with the handle
+               eType - the type of resource
+
+ @Output       phHandle - points to handle
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVFindHandle(PVRSRV_HANDLE_BASE *psBase, IMG_SID *phHandle, IMG_VOID *pvData, PVRSRV_HANDLE_TYPE eType)
 #else
@@ -1344,9 +1898,9 @@ PVRSRV_ERROR PVRSRVFindHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle,
        IMG_HANDLE hHandle;
 #endif
 
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 
-       
+       /* See if there is a handle for this data pointer */
 #if defined (SUPPORT_SID_INTERFACE)
        hHandle = (IMG_SID) FindHandle(psBase, pvData, eType, IMG_NULL);
 #else
@@ -1362,6 +1916,23 @@ PVRSRV_ERROR PVRSRVFindHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE *phHandle,
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVLookupHandleAnyType
+
+ @Description  Lookup the data pointer and type corresponding to a handle
+
+ @Input                ppvData - location to return data pointer
+               peType - location to return handle type
+               hHandle - handle from client
+
+ @Output       ppvData - points to the data pointer
+               peType - points to handle type
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVLookupHandleAnyType(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvData, PVRSRV_HANDLE_TYPE *peType, IMG_SID hHandle)
 #else
@@ -1387,6 +1958,22 @@ PVRSRV_ERROR PVRSRVLookupHandleAnyType(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *pp
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVLookupHandle
+
+ @Description  Lookup the data pointer corresponding to a handle
+
+ @Input                ppvData - location to return data pointer
+               hHandle - handle from client
+               eType - handle type
+
+ @Output       ppvData - points to the data pointer
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVLookupHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvData, IMG_SID hHandle, PVRSRV_HANDLE_TYPE eType)
 #else
@@ -1396,9 +1983,9 @@ PVRSRV_ERROR PVRSRVLookupHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvData,
        struct sHandle *psHandle;
        PVRSRV_ERROR eError;
 
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 #if defined (SUPPORT_SID_INTERFACE)
-       PVR_ASSERT(hHandle != 0)
+       PVR_ASSERT(hHandle != 0);
 #endif
 
        eError = GetHandleStructure(psBase, &psHandle, hHandle, eType);
@@ -1416,6 +2003,23 @@ PVRSRV_ERROR PVRSRVLookupHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvData,
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVLookupSubHandle
+
+ @Description  Lookup the data pointer corresponding to a subhandle
+
+ @Input                ppvData - location to return data pointer
+               hHandle - handle from client
+               eType - handle type
+               hAncestor - ancestor handle
+
+ @Output       ppvData - points to the data pointer
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVLookupSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvData, IMG_SID hHandle, PVRSRV_HANDLE_TYPE eType, IMG_SID hAncestor)
 #else
@@ -1426,9 +2030,9 @@ PVRSRV_ERROR PVRSRVLookupSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvDat
        struct sHandle *psCHand;
        PVRSRV_ERROR eError;
 
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 #if defined (SUPPORT_SID_INTERFACE)
-       PVR_ASSERT(hHandle != 0)
+       PVR_ASSERT(hHandle != 0);
 #endif
 
        eError = GetHandleStructure(psBase, &psCHand, hHandle, eType);
@@ -1438,7 +2042,7 @@ PVRSRV_ERROR PVRSRVLookupSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvDat
                return eError;
        }
 
-       
+       /* Look for hAncestor among the handle's ancestors */
        for (psPHand = psCHand; ParentHandle(psPHand) != hAncestor; )
        {
                eError = GetHandleStructure(psBase, &psPHand, ParentHandle(psPHand), PVRSRV_HANDLE_TYPE_NONE);
@@ -1454,6 +2058,24 @@ PVRSRV_ERROR PVRSRVLookupSubHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvDat
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVGetParentHandle
+
+ @Description  Lookup the parent of a handle
+
+ @Input                phParent - location for returning parent handle
+               hHandle - handle for which the parent handle is required
+               eType - handle type
+               hParent - parent handle
+
+ @Output       *phParent - parent handle, or IMG_NULL if there is no parent
+
+ @Return       Error code or PVRSRV_OK.  Note that not having a parent is
+               not regarded as an error.
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVGetParentHandle(PVRSRV_HANDLE_BASE *psBase, IMG_SID *phParent, IMG_SID hHandle, PVRSRV_HANDLE_TYPE eType)
 #else
@@ -1463,7 +2085,7 @@ PVRSRV_ERROR PVRSRVGetParentHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *phPare
        struct sHandle *psHandle;
        PVRSRV_ERROR eError;
 
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 
        eError = GetHandleStructure(psBase, &psHandle, hHandle, eType);
        if (eError != PVRSRV_OK)
@@ -1477,6 +2099,23 @@ PVRSRV_ERROR PVRSRVGetParentHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *phPare
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVLookupAndReleaseHandle
+
+ @Description  Lookup the data pointer corresponding to a handle
+
+ @Input                ppvData - location to return data pointer
+               hHandle - handle from client
+               eType - handle type
+               eFlag - lookup flags
+
+ @Output       ppvData - points to the data pointer
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVLookupAndReleaseHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvData, IMG_SID hHandle, PVRSRV_HANDLE_TYPE eType)
 #else
@@ -1486,7 +2125,7 @@ PVRSRV_ERROR PVRSRVLookupAndReleaseHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID
        struct sHandle *psHandle;
        PVRSRV_ERROR eError;
 
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 
        eError = GetHandleStructure(psBase, &psHandle, hHandle, eType);
        if (eError != PVRSRV_OK)
@@ -1505,6 +2144,19 @@ PVRSRV_ERROR PVRSRVLookupAndReleaseHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVReleaseHandle
+
+ @Description  Release a handle that is no longer needed
+
+ @Input        hHandle - handle from client
+               eType - handle type
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR PVRSRVReleaseHandle(PVRSRV_HANDLE_BASE *psBase, IMG_SID hHandle, PVRSRV_HANDLE_TYPE eType)
 #else
@@ -1514,7 +2166,7 @@ PVRSRV_ERROR PVRSRVReleaseHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE hHandle,
        struct sHandle *psHandle;
        PVRSRV_ERROR eError;
 
-       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE)
+       PVR_ASSERT(eType != PVRSRV_HANDLE_TYPE_NONE);
 
        eError = GetHandleStructure(psBase, &psHandle, hHandle, eType);
        if (eError != PVRSRV_OK)
@@ -1528,6 +2180,19 @@ PVRSRV_ERROR PVRSRVReleaseHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE hHandle,
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVNewHandleBatch
+
+ @Description  Start a new handle batch
+
+ @Input        psBase          - handle base
+ @Input        ui32BatchSize   - handle batch size
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVNewHandleBatch(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32BatchSize)
 {
        PVRSRV_ERROR eError;
@@ -1553,18 +2218,31 @@ PVRSRV_ERROR PVRSRVNewHandleBatch(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32Bat
 
        psBase->ui32HandBatchSize = ui32BatchSize;
 
-       
+       /* Record current number of handles */
        psBase->ui32TotalHandCountPreBatch = psBase->ui32TotalHandCount;
 
-       PVR_ASSERT(psBase->ui32BatchHandAllocFailures == 0)
+       PVR_ASSERT(psBase->ui32BatchHandAllocFailures == 0);
 
-       PVR_ASSERT(psBase->ui32FirstBatchIndexPlusOne == 0)
+       PVR_ASSERT(psBase->ui32FirstBatchIndexPlusOne == 0);
 
-       PVR_ASSERT(HANDLES_BATCHED(psBase))
+       PVR_ASSERT(HANDLES_BATCHED(psBase));
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVHandleBatchCommitOrRelease
+
+ @Description  Release a handle batch
+
+ @Input        psBase  - handle base
+               bCommit - commit handles
+
+ @Return       none
+
+******************************************************************************/
 static PVRSRV_ERROR PVRSRVHandleBatchCommitOrRelease(PVRSRV_HANDLE_BASE *psBase, IMG_BOOL bCommit)
 {
 
@@ -1586,15 +2264,18 @@ static PVRSRV_ERROR PVRSRVHandleBatchCommitOrRelease(PVRSRV_HANDLE_BASE *psBase,
                }
                bCommitBatch = IMG_FALSE;
        }
-       
-       PVR_ASSERT(psBase->ui32BatchHandAllocFailures == 0 || !bCommit)
+       /*
+        * The whole point of batched handles is to avoid handle allocation
+        * failures.
+        */
+       PVR_ASSERT(psBase->ui32BatchHandAllocFailures == 0 || !bCommit);
 
        ui32IndexPlusOne = psBase->ui32FirstBatchIndexPlusOne;
        while(ui32IndexPlusOne != 0)
        {
                struct sHandle *psHandle = INDEX_TO_HANDLE_STRUCT_PTR(psBase, ui32IndexPlusOne - 1);
                IMG_UINT32 ui32NextIndexPlusOne = psHandle->ui32NextIndexPlusOne;
-               PVR_ASSERT(BATCHED_HANDLE(psHandle))
+               PVR_ASSERT(BATCHED_HANDLE(psHandle));
 
                psHandle->ui32NextIndexPlusOne = 0;
 
@@ -1602,11 +2283,15 @@ static PVRSRV_ERROR PVRSRVHandleBatchCommitOrRelease(PVRSRV_HANDLE_BASE *psBase,
                {
                        PVRSRV_ERROR eError;
 
-                       
+                       /*
+                        * We need a complete free here.  If the handle
+                        * is not partially free, set the handle as
+                        * unbatched to avoid a partial free.
+                        */
                        if (!BATCHED_HANDLE_PARTIALLY_FREE(psHandle))
                        {
-                                
-                               SET_UNBATCHED_HANDLE(psHandle);  
+                               /* PRQA S 1474,4130 1 */ /* ignore warnings about enum types being modified */
+                               SET_UNBATCHED_HANDLE(psHandle); /* PRQA S 4130 */ /* mis-use of enums FIXME*/
                        }
 
                        eError = FreeHandle(psBase, psHandle);
@@ -1614,11 +2299,11 @@ static PVRSRV_ERROR PVRSRVHandleBatchCommitOrRelease(PVRSRV_HANDLE_BASE *psBase,
                        {
                                 PVR_DPF((PVR_DBG_ERROR, "PVRSRVHandleBatchCommitOrRelease: Error freeing handle (%d)", eError));
                        }
-                       PVR_ASSERT(eError == PVRSRV_OK)
+                       PVR_ASSERT(eError == PVRSRV_OK);
                }
                else
                {
-                        
+                       /* PRQA S 1474,4130 1 */ /* ignore warnings about enum types being modified */
                        SET_UNBATCHED_HANDLE(psHandle);
                }
 
@@ -1630,7 +2315,7 @@ static PVRSRV_ERROR PVRSRVHandleBatchCommitOrRelease(PVRSRV_HANDLE_BASE *psBase,
        {
                IMG_UINT32 ui32Delta = psBase->ui32TotalHandCount - psBase->ui32TotalHandCountPreBatch;
 
-               PVR_ASSERT(psBase->ui32TotalHandCount > psBase->ui32TotalHandCountPreBatch)
+               PVR_ASSERT(psBase->ui32TotalHandCount > psBase->ui32TotalHandCountPreBatch);
 
                PVR_DPF((PVR_DBG_WARNING, "PVRSRVHandleBatchCommitOrRelease: The batch size was too small.  Batch size was %u, but needs to be %u", psBase->ui32HandBatchSize,  psBase->ui32HandBatchSize + ui32Delta));
 
@@ -1644,7 +2329,7 @@ static PVRSRV_ERROR PVRSRVHandleBatchCommitOrRelease(PVRSRV_HANDLE_BASE *psBase,
 
        if (psBase->ui32BatchHandAllocFailures != 0 && bCommit)
        {
-               PVR_ASSERT(!bCommitBatch)
+               PVR_ASSERT(!bCommitBatch);
 
                return PVRSRV_ERROR_HANDLE_BATCH_COMMIT_FAILURE;
        }
@@ -1652,16 +2337,53 @@ static PVRSRV_ERROR PVRSRVHandleBatchCommitOrRelease(PVRSRV_HANDLE_BASE *psBase,
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVCommitHandleBatch
+
+ @Description  Commit a handle batch
+
+ @Input        psBase  - handle base
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVCommitHandleBatch(PVRSRV_HANDLE_BASE *psBase)
 {
        return PVRSRVHandleBatchCommitOrRelease(psBase, IMG_TRUE);
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRReleaseHandleBatch
+
+ @Description  Release a handle batch
+
+ @Input        psBase  - handle base
+
+ @Return       none
+
+******************************************************************************/
 IMG_VOID PVRSRVReleaseHandleBatch(PVRSRV_HANDLE_BASE *psBase)
 {
        (IMG_VOID) PVRSRVHandleBatchCommitOrRelease(psBase, IMG_FALSE);
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSetMaxHandle
+
+ @Description  Set maximum handle number for given handle base
+
+ @Input        psBase - pointer to handle base structure
+               ui32MaxHandle - Maximum handle number
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVSetMaxHandle(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32MaxHandle)
 {
        IMG_UINT32 ui32MaxHandleRounded;
@@ -1672,7 +2394,7 @@ PVRSRV_ERROR PVRSRVSetMaxHandle(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32MaxHa
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* Validate the limit */
        if (ui32MaxHandle  == 0 || ui32MaxHandle > DEFAULT_MAX_HANDLE)
        {
                PVR_DPF((PVR_DBG_ERROR, "PVRSRVSetMaxHandle: Limit must be between %u and %u, inclusive", 0, DEFAULT_MAX_HANDLE));
@@ -1680,7 +2402,7 @@ PVRSRV_ERROR PVRSRVSetMaxHandle(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32MaxHa
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* The limit can only be set if no handles have been allocated */
        if (psBase->ui32TotalHandCount != 0)
        {
                PVR_DPF((PVR_DBG_ERROR, "PVRSRVSetMaxHandle: Limit cannot be set because handles have already been allocated"));
@@ -1690,24 +2412,54 @@ PVRSRV_ERROR PVRSRVSetMaxHandle(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32MaxHa
 
        ui32MaxHandleRounded = ROUND_DOWN_TO_MULTIPLE_OF_BLOCK_SIZE(ui32MaxHandle);
 
-       
+       /*
+        * Allow the maximum number of handles to be reduced, but never to
+        * zero.
+        */
        if (ui32MaxHandleRounded != 0 && ui32MaxHandleRounded < psBase->ui32MaxIndexPlusOne)
        {
                psBase->ui32MaxIndexPlusOne = ui32MaxHandleRounded;
        }
 
-       PVR_ASSERT(psBase->ui32MaxIndexPlusOne != 0)
-       PVR_ASSERT(psBase->ui32MaxIndexPlusOne <= DEFAULT_MAX_INDEX_PLUS_ONE)
-       PVR_ASSERT((psBase->ui32MaxIndexPlusOne % HANDLE_BLOCK_SIZE) == 0)
+       PVR_ASSERT(psBase->ui32MaxIndexPlusOne != 0);
+       PVR_ASSERT(psBase->ui32MaxIndexPlusOne <= DEFAULT_MAX_INDEX_PLUS_ONE);
+       PVR_ASSERT((psBase->ui32MaxIndexPlusOne % HANDLE_BLOCK_SIZE) == 0);
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVGetMaxHandle
+
+ @Description  Get maximum handle number for given handle base
+
+ @Input        psBase - pointer to handle base structure
+
+ @Output       Maximum handle number, or 0 if handle limits not
+               supported.
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 IMG_UINT32 PVRSRVGetMaxHandle(PVRSRV_HANDLE_BASE *psBase)
 {
        return psBase->ui32MaxIndexPlusOne;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVEnableHandlePurging
+
+ @Description  Enable purging for a given handle base
+
+ @Input        psBase - pointer to handle base structure
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVEnableHandlePurging(PVRSRV_HANDLE_BASE *psBase)
 {
        if (psBase->bPurgingEnabled)
@@ -1716,7 +2468,7 @@ PVRSRV_ERROR PVRSRVEnableHandlePurging(PVRSRV_HANDLE_BASE *psBase)
                return PVRSRV_OK;
        }
 
-       
+       /* Purging can only be enabled if no handles have been allocated */
        if (psBase->ui32TotalHandCount != 0)
        {
                PVR_DPF((PVR_DBG_ERROR, "PVRSRVEnableHandlePurging: Handles have already been allocated"));
@@ -1728,6 +2480,18 @@ PVRSRV_ERROR PVRSRVEnableHandlePurging(PVRSRV_HANDLE_BASE *psBase)
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVPurgeHandles
+
+ @Description  Purge handles for a given handle base
+
+ @Input        psBase - pointer to handle base structure
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVPurgeHandles(PVRSRV_HANDLE_BASE *psBase)
 {
        IMG_UINT32 ui32BlockIndex;
@@ -1745,7 +2509,7 @@ PVRSRV_ERROR PVRSRVPurgeHandles(PVRSRV_HANDLE_BASE *psBase)
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       PVR_ASSERT((psBase->ui32TotalHandCount % HANDLE_BLOCK_SIZE) == 0)
+       PVR_ASSERT((psBase->ui32TotalHandCount % HANDLE_BLOCK_SIZE) == 0);
 
        for (ui32BlockIndex = INDEX_TO_BLOCK_INDEX(psBase->ui32TotalHandCount); ui32BlockIndex != 0; ui32BlockIndex--)
        {
@@ -1756,12 +2520,14 @@ PVRSRV_ERROR PVRSRVPurgeHandles(PVRSRV_HANDLE_BASE *psBase)
        }
        ui32NewHandCount = BLOCK_INDEX_TO_INDEX(ui32BlockIndex);
 
-       
+       /*
+        * Check for a suitable decrease in the handle count.
+        */
        if (ui32NewHandCount <= (psBase->ui32TotalHandCount/2))
        {
                PVRSRV_ERROR eError;
 
-               
+               // PVR_TRACE((" PVRSRVPurgeHandles: reducing number of handles from %u to %u", psBase->ui32TotalHandCount, ui32NewHandCount));
 
                eError = ReallocHandleArray(psBase, ui32NewHandCount);
                if (eError != PVRSRV_OK)
@@ -1773,6 +2539,20 @@ PVRSRV_ERROR PVRSRVPurgeHandles(PVRSRV_HANDLE_BASE *psBase)
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVAllocHandleBase
+
+ @Description  Allocate a handle base structure for a process
+
+ @Input        ppsBase - pointer to handle base structure pointer
+
+ @Output       ppsBase - points to handle base structure pointer
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVAllocHandleBase(PVRSRV_HANDLE_BASE **ppsBase)
 {
        PVRSRV_HANDLE_BASE *psBase;
@@ -1791,7 +2571,7 @@ PVRSRV_ERROR PVRSRVAllocHandleBase(PVRSRV_HANDLE_BASE **ppsBase)
        }
        OSMemSet(psBase, 0, sizeof(*psBase));
 
-       
+       /* Create hash table */
        psBase->psHashTab = HASH_Create_Extended(HANDLE_HASH_TAB_INIT_SIZE, sizeof(HAND_KEY), HASH_Func_Default, HASH_Key_Comp_Default);
        if (psBase->psHashTab == IMG_NULL)
        {
@@ -1809,11 +2589,23 @@ PVRSRV_ERROR PVRSRVAllocHandleBase(PVRSRV_HANDLE_BASE **ppsBase)
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVFreeHandleBase
+
+ @Description  Free a handle base structure
+
+ @Input        psBase - pointer to handle base structure
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVFreeHandleBase(PVRSRV_HANDLE_BASE *psBase)
 {
        PVRSRV_ERROR eError;
 
-       PVR_ASSERT(psBase != gpsKernelHandleBase)
+       PVR_ASSERT(psBase != gpsKernelHandleBase);
 
        eError = FreeHandleBase(psBase);
        if (eError != PVRSRV_OK)
@@ -1824,11 +2616,21 @@ PVRSRV_ERROR PVRSRVFreeHandleBase(PVRSRV_HANDLE_BASE *psBase)
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVHandleInit
+
+ @Description  Initialise handle management
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVHandleInit(IMG_VOID)
 {
        PVRSRV_ERROR eError;
 
-       PVR_ASSERT(gpsKernelHandleBase == IMG_NULL)
+       PVR_ASSERT(gpsKernelHandleBase == IMG_NULL);
 
        eError = PVRSRVAllocHandleBase(&gpsKernelHandleBase);
        if (eError != PVRSRV_OK)
@@ -1850,6 +2652,16 @@ error:
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVHandleDeInit
+
+ @Description  De-initialise handle management
+
+ @Return       Error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVHandleDeInit(IMG_VOID)
 {
        PVRSRV_ERROR eError = PVRSRV_OK;
@@ -1870,4 +2682,8 @@ PVRSRV_ERROR PVRSRVHandleDeInit(IMG_VOID)
        return eError;
 }
 #else
-#endif 
+/* disable warning about empty module */
+#endif /* #if defined(PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE) */
+/******************************************************************************
+ End of file (handle.c)
+******************************************************************************/
index 78eab44..1569425 100644 (file)
@@ -1,28 +1,49 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Self scaling hash tables.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description
+   Implements simple self scaling hash tables. Hash collisions are
+   handled by chaining entries together. Hash tables are increased in
+   size when they become more than (50%?) full and decreased in size
+   when less than (25%?) full. Hash tables are never decreased below
+   their initial size.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "pvr_debug.h"
 #include "img_defs.h"
 #define        KEY_COMPARE(pHash, pKey1, pKey2) \
        ((pHash)->pfnKeyComp((pHash)->uKeySize, (pKey1), (pKey2)))
 
+/* Each entry in a hash table is placed into a bucket */
 struct _BUCKET_
 {
-       
+       /* the next bucket on the same chain */
        struct _BUCKET_ *pNext;
 
-       
+       /* entry value */
        IMG_UINTPTR_T v;
 
-       
-       IMG_UINTPTR_T k[];               
+       /* entry key */
+       IMG_UINTPTR_T k[];              /* PRQA S 0642 */ /* override dynamic array declaration warning */
 };
 typedef struct _BUCKET_ BUCKET;
 
 struct _HASH_TABLE_
 {
-       
+       /* the hash table array */
        BUCKET **ppBucketTable;
 
-       
+       /* current size of the hash table */
        IMG_UINT32 uSize;
 
-       
+       /* number of entries currently in the hash table */
        IMG_UINT32 uCount;
 
-       
+       /* the minimum size that the hash table should be re-sized to */
        IMG_UINT32 uMinimumSize;
 
-       
+       /* size of key in bytes */
        IMG_UINT32 uKeySize;
 
-       
+       /* hash function */
        HASH_FUNC *pfnHashFunc;
 
-       
+       /* key comparison function */
        HASH_KEY_COMP *pfnKeyComp;
 };
 
+/*!
+******************************************************************************
+       @Function       HASH_Func_Default
+
+       @Description    Hash function intended for hashing keys composed of
+                    IMG_UINTPTR_T arrays.
+
+       @Input          uKeySize - the size of the hash key, in bytes.
+       @Input          pKey - a pointer to the key to hash.
+       @Input          uHashTabLen - the length of the hash table.
+    
+       @Return             the hash value.
+******************************************************************************/
 IMG_UINT32
 HASH_Func_Default (IMG_SIZE_T uKeySize, IMG_VOID *pKey, IMG_UINT32 uHashTabLen)
 {
@@ -107,6 +142,18 @@ HASH_Func_Default (IMG_SIZE_T uKeySize, IMG_VOID *pKey, IMG_UINT32 uHashTabLen)
        return uHashKey;
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Key_Comp_Default
+
+       @Description    Compares keys composed of IMG_UINTPTR_T arrays.
+
+       @Input          uKeySize - the size of the hash key, in bytes.
+       @Input          pKey1 - pointer to first hash key to compare.
+       @Input          pKey2 - pointer to second hash key to compare.
+       @Return             IMG_TRUE  - the keys match.
+                    IMG_FALSE - the keys don't match.
+******************************************************************************/
 IMG_BOOL
 HASH_Key_Comp_Default (IMG_SIZE_T uKeySize, IMG_VOID *pKey1, IMG_VOID *pKey2)
 {
@@ -126,6 +173,18 @@ HASH_Key_Comp_Default (IMG_SIZE_T uKeySize, IMG_VOID *pKey1, IMG_VOID *pKey2)
        return IMG_TRUE;
 }
 
+/*!
+******************************************************************************
+       @Function       _ChainInsert
+
+       @Description    Insert a bucket into the appropriate hash table chain.
+
+       @Input          pBucket - the bucket
+       @Input          ppBucketTable - the hash table
+       @Input          uSize - the size of the hash table
+    
+       @Return         PVRSRV_ERROR
+******************************************************************************/
 static PVRSRV_ERROR
 _ChainInsert (HASH_TABLE *pHash, BUCKET *pBucket, BUCKET **ppBucketTable, IMG_UINT32 uSize)
 {
@@ -141,13 +200,27 @@ _ChainInsert (HASH_TABLE *pHash, BUCKET *pBucket, BUCKET **ppBucketTable, IMG_UI
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       uIndex = KEY_TO_INDEX(pHash, pBucket->k, uSize);         
+       uIndex = KEY_TO_INDEX(pHash, pBucket->k, uSize);        /* PRQA S 0432,0541 */ /* ignore dynamic array warning */
        pBucket->pNext = ppBucketTable[uIndex];
        ppBucketTable[uIndex] = pBucket;
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+       @Function       _Rehash
+
+       @Description    Iterate over every entry in an old hash table and
+                    rehash into the new table.
+
+       @Input          ppOldTable - the old hash table
+       @Input          uOldSize - the size of the old hash table
+       @Input          ppNewTable - the new hash table
+       @Input          uNewSize - the size of the new hash table
+    
+       @Return         None
+******************************************************************************/
 static PVRSRV_ERROR
 _Rehash (HASH_TABLE *pHash,
         BUCKET **ppOldTable, IMG_UINT32 uOldSize,
@@ -174,6 +247,20 @@ _Rehash (HASH_TABLE *pHash,
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+       @Function       _Resize
+
+       @Description    Attempt to resize a hash table, failure to allocate a
+                    new larger hash table is not considered a hard failure.
+                    We simply continue and allow the table to fill up, the
+                       effect is to allow hash chains to become longer.
+
+       @Input          pHash - Hash table to resize.
+    @Input          uNewSize - Required table size.
+       @Return         IMG_TRUE Success
+                       IMG_FALSE Failed
+******************************************************************************/
 static IMG_BOOL
 _Resize (HASH_TABLE *pHash, IMG_UINT32 uNewSize)
 {
@@ -202,7 +289,7 @@ _Resize (HASH_TABLE *pHash, IMG_UINT32 uNewSize)
                }
 
         OSFreeMem (PVRSRV_PAGEABLE_SELECT, sizeof(BUCKET *)*pHash->uSize, pHash->ppBucketTable, IMG_NULL);
-        
+        /*not nulling pointer, being reassigned just below*/
         pHash->ppBucketTable = ppNewTable;
         pHash->uSize = uNewSize;
     }
@@ -210,6 +297,23 @@ _Resize (HASH_TABLE *pHash, IMG_UINT32 uNewSize)
 }
 
 
+/*!
+******************************************************************************
+       @Function       HASH_Create_Extended
+
+       @Description    Create a self scaling hash table, using the supplied
+                    key size, and the supplied hash and key comparsion
+                    functions.
+
+       @Input          uInitialLen - initial and minimum length of the
+                    hash table, where the length refers to the number
+                    of entries in the hash table, not its size in
+                    bytes.
+       @Input          uKeySize - the size of the key, in bytes.
+       @Input          pfnHashFunc - pointer to hash function.
+    @Input          pfnKeyComp - pointer to key comparsion function.
+       @Return         IMG_NULL or hash table handle.
+******************************************************************************/
 HASH_TABLE * HASH_Create_Extended (IMG_UINT32 uInitialLen, IMG_SIZE_T uKeySize, HASH_FUNC *pfnHashFunc, HASH_KEY_COMP *pfnKeyComp)
 {
        HASH_TABLE *pHash;
@@ -240,7 +344,7 @@ HASH_TABLE * HASH_Create_Extended (IMG_UINT32 uInitialLen, IMG_SIZE_T uKeySize,
        if (pHash->ppBucketTable == IMG_NULL)
     {
                OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(HASH_TABLE), pHash, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
                return IMG_NULL;
     }
 
@@ -249,12 +353,38 @@ HASH_TABLE * HASH_Create_Extended (IMG_UINT32 uInitialLen, IMG_SIZE_T uKeySize,
        return pHash;
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Create
+
+       @Description    Create a self scaling hash table with a key
+                    consisting of a single IMG_UINTPTR_T, and using
+                    the default hash and key comparison functions.
+
+       @Input          uInitialLen - initial and minimum length of the
+                    hash table, where the length refers to the
+                    number of entries in the hash table, not its size
+                    in bytes.
+       @Return             IMG_NULL or hash table handle.
+******************************************************************************/
 HASH_TABLE * HASH_Create (IMG_UINT32 uInitialLen)
 {
        return HASH_Create_Extended(uInitialLen, sizeof(IMG_UINTPTR_T),
                &HASH_Func_Default, &HASH_Key_Comp_Default);
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Delete
+
+       @Description    Delete a hash table created by HASH_Create_Extended or
+                    HASH_Create.  All entries in the table must have been
+                    removed before calling this function.
+
+       @Input          pHash - hash table
+    
+       @Return             None
+******************************************************************************/
 IMG_VOID
 HASH_Delete (HASH_TABLE *pHash)
 {
@@ -271,10 +401,24 @@ HASH_Delete (HASH_TABLE *pHash)
                OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(BUCKET *)*pHash->uSize, pHash->ppBucketTable, IMG_NULL);
                pHash->ppBucketTable = IMG_NULL;
                OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(HASH_TABLE), pHash, IMG_NULL);
-               
+               /*not nulling pointer, copy on stack*/
     }
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Insert_Extended
+
+       @Description    Insert a key value pair into a hash table created
+                    with HASH_Create_Extended.
+
+       @Input          pHash - the hash table.
+       @Input          pKey - pointer to the key.
+       @Input          v - the value associated with the key.
+
+       @Return             IMG_TRUE  - success
+                       IMG_FALSE  - failure
+******************************************************************************/
 IMG_BOOL
 HASH_Insert_Extended (HASH_TABLE *pHash, IMG_VOID *pKey, IMG_UINTPTR_T v)
 {
@@ -301,7 +445,7 @@ HASH_Insert_Extended (HASH_TABLE *pHash, IMG_VOID *pKey, IMG_UINTPTR_T v)
        }
 
        pBucket->v = v;
-        
+       /* PRQA S 0432,0541 1 */ /* ignore warning about dynamic array k (linux)*/
        OSMemCopy(pBucket->k, pKey, pHash->uKeySize);
        if (_ChainInsert (pHash, pBucket, pHash->ppBucketTable, pHash->uSize) != PVRSRV_OK)
        {
@@ -313,11 +457,12 @@ HASH_Insert_Extended (HASH_TABLE *pHash, IMG_VOID *pKey, IMG_UINTPTR_T v)
 
        pHash->uCount++;
 
-       
+       /* check if we need to think about re-balencing */
        if (pHash->uCount << 1 > pHash->uSize)
     {
-        
-
+        /* Ignore the return code from _Resize because the hash table is
+           still in a valid state and although not ideally sized, it is still
+           functional */
         _Resize (pHash, pHash->uSize << 1);
     }
 
@@ -325,6 +470,20 @@ HASH_Insert_Extended (HASH_TABLE *pHash, IMG_VOID *pKey, IMG_UINTPTR_T v)
        return IMG_TRUE;
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Insert
+
+       @Description    Insert a key value pair into a hash table created with
+                    HASH_Create.
+
+       @Input          pHash - the hash table.
+       @Input          k - the key value.
+       @Input          v - the value associated with the key.
+
+       @Return             IMG_TRUE - success.
+                       IMG_FALSE - failure.
+******************************************************************************/
 IMG_BOOL
 HASH_Insert (HASH_TABLE *pHash, IMG_UINTPTR_T k, IMG_UINTPTR_T v)
 {
@@ -335,6 +494,19 @@ HASH_Insert (HASH_TABLE *pHash, IMG_UINTPTR_T k, IMG_UINTPTR_T v)
        return HASH_Insert_Extended(pHash, &k, v);
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Remove_Extended
+
+       @Description    Remove a key from a hash table created with
+                    HASH_Create_Extended.
+
+       @Input          pHash - the hash table.
+       @Input          pKey - pointer to key.
+
+       @Return             0 if the key is missing, or the value associated
+                    with the key.
+******************************************************************************/
 IMG_UINTPTR_T
 HASH_Remove_Extended(HASH_TABLE *pHash, IMG_VOID *pKey)
 {
@@ -356,7 +528,7 @@ HASH_Remove_Extended(HASH_TABLE *pHash, IMG_VOID *pKey)
 
        for (ppBucket = &(pHash->ppBucketTable[uIndex]); *ppBucket != IMG_NULL; ppBucket = &((*ppBucket)->pNext))
        {
-                
+               /* PRQA S 0432,0541 1 */ /* ignore warning about dynamic array k */
                if (KEY_COMPARE(pHash, (*ppBucket)->k, pKey))
                {
                        BUCKET *pBucket = *ppBucket;
@@ -364,16 +536,17 @@ HASH_Remove_Extended(HASH_TABLE *pHash, IMG_VOID *pKey)
                        (*ppBucket) = pBucket->pNext;
 
                        OSFreeMem(PVRSRV_PAGEABLE_SELECT, sizeof(BUCKET) + pHash->uKeySize, pBucket, IMG_NULL);
-                       
+                       /*not nulling original pointer, already overwritten*/
 
                        pHash->uCount--;
 
-                       
+                       /* check if we need to think about re-balencing */
                        if (pHash->uSize > (pHash->uCount << 2) &&
                 pHash->uSize > pHash->uMinimumSize)
             {
-                
-
+                /* Ignore the return code from _Resize because the
+                   hash table is still in a valid state and although
+                   not ideally sized, it is still functional */
                                _Resize (pHash,
                          PRIVATE_MAX (pHash->uSize >> 1,
                                       pHash->uMinimumSize));
@@ -391,6 +564,19 @@ HASH_Remove_Extended(HASH_TABLE *pHash, IMG_VOID *pKey)
        return 0;
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Remove
+
+       @Description    Remove a key value pair from a hash table created
+                    with HASH_Create.
+
+       @Input          pHash - the hash table
+       @Input          k - the key
+
+       @Return         0 if the key is missing, or the value associated
+                    with the key.
+******************************************************************************/
 IMG_UINTPTR_T
 HASH_Remove (HASH_TABLE *pHash, IMG_UINTPTR_T k)
 {
@@ -400,6 +586,19 @@ HASH_Remove (HASH_TABLE *pHash, IMG_UINTPTR_T k)
        return HASH_Remove_Extended(pHash, &k);
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Retrieve_Extended
+
+       @Description    Retrieve a value from a hash table created with
+                    HASH_Create_Extended.
+
+       @Input          pHash - the hash table.
+       @Input          pKey - pointer to the key.
+
+       @Return             0 if the key is missing, or the value associated with
+                    the key.
+******************************************************************************/
 IMG_UINTPTR_T
 HASH_Retrieve_Extended (HASH_TABLE *pHash, IMG_VOID *pKey)
 {
@@ -421,7 +620,7 @@ HASH_Retrieve_Extended (HASH_TABLE *pHash, IMG_VOID *pKey)
 
        for (ppBucket = &(pHash->ppBucketTable[uIndex]); *ppBucket != IMG_NULL; ppBucket = &((*ppBucket)->pNext))
        {
-                
+               /* PRQA S 0432,0541 1 */ /* ignore warning about dynamic array k */
                if (KEY_COMPARE(pHash, (*ppBucket)->k, pKey))
                {
                        BUCKET *pBucket = *ppBucket;
@@ -439,6 +638,18 @@ HASH_Retrieve_Extended (HASH_TABLE *pHash, IMG_VOID *pKey)
        return 0;
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Retrieve
+
+       @Description    Retrieve a value from a hash table created with
+                    HASH_Create.
+
+       @Input          pHash - the hash table
+       @Input          k - the key
+       @Return             0 if the key is missing, or the value associated with
+                    the key.
+******************************************************************************/
 IMG_UINTPTR_T
 HASH_Retrieve (HASH_TABLE *pHash, IMG_UINTPTR_T k)
 {
@@ -447,6 +658,17 @@ HASH_Retrieve (HASH_TABLE *pHash, IMG_UINTPTR_T k)
        return HASH_Retrieve_Extended(pHash, &k);
 }
 
+/*!
+******************************************************************************
+       @Function       HASH_Iterate
+
+       @Description    Iterate over every entry in the hash table
+
+       @Input          pHash - the old hash table
+       @Input          pfnCallback - the size of the old hash table
+
+       @Return             Callback error if any, otherwise PVRSRV_OK
+******************************************************************************/
 PVRSRV_ERROR
 HASH_Iterate(HASH_TABLE *pHash, HASH_pfnCallback pfnCallback)
 {
@@ -462,7 +684,7 @@ HASH_Iterate(HASH_TABLE *pHash, HASH_pfnCallback pfnCallback)
                        
                        eError = pfnCallback((IMG_UINTPTR_T) ((IMG_VOID *) *(pBucket->k)), (IMG_UINTPTR_T) pBucket->v);
 
-                       
+                       /* The callback might want us to break out early */
                        if (eError != PVRSRV_OK)
                                return eError;
 
@@ -473,6 +695,17 @@ HASH_Iterate(HASH_TABLE *pHash, HASH_pfnCallback pfnCallback)
 }
 
 #ifdef HASH_TRACE
+/*!
+******************************************************************************
+       @Function       HASH_Dump
+
+       @Description    To dump the contents of a hash table in human readable
+                    form.
+
+       @Input          pHash - the hash table
+
+       @Return             None
+******************************************************************************/
 IMG_VOID
 HASH_Dump (HASH_TABLE *pHash)
 {
index 1081781..c6e1ee8 100644 (file)
@@ -1,32 +1,53 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linked list shared functions implementation
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Implementation of the list iterators for types shared among
+                more than one file in the services code.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #include "lists.h"
 #include "services_headers.h"
 
+/*===================================================================
+  LIST ITERATOR FUNCTIONS USED IN MORE THAN ONE FILE (those used just
+  once are implemented locally).
+  ===================================================================*/
+
 IMPLEMENT_LIST_ANY_VA(BM_HEAP)
 IMPLEMENT_LIST_ANY_2(BM_HEAP, PVRSRV_ERROR, PVRSRV_OK)
 IMPLEMENT_LIST_ANY_VA_2(BM_HEAP, PVRSRV_ERROR, PVRSRV_OK)
@@ -55,6 +76,27 @@ IMPLEMENT_LIST_INSERT(PVRSRV_POWER_DEV)
 IMPLEMENT_LIST_REMOVE(PVRSRV_POWER_DEV)
 
 
+/*===================================================================
+  BELOW ARE IMPLEMENTED SOME COMMON CALLBACKS USED IN DIFFERENT FILES
+  ===================================================================*/
+
+
+/*!
+******************************************************************************
+       @Function   MatchDeviceKM_AnyVaCb
+       @Description Matchs a device node with an id and optionally a class.
+
+       @Input      psDeviceNode - Pointer to the device node.
+    @Input      va - Variable argument list, with te following values:
+                                       # ui32DevIndex - Index of de device to match.
+                                       # bIgnoreClass - Flag indicating if there's
+                                               no need to check the device class.
+                                       # eDevClass - Device class, ONLY present if
+                                               bIgnoreClass was IMG_FALSE.
+
+       @Return         The pointer to the device node if it matchs, IMG_NULL
+                otherwise.
+******************************************************************************/
 IMG_VOID* MatchDeviceKM_AnyVaCb(PVRSRV_DEVICE_NODE* psDeviceNode, va_list va)
 {
        IMG_UINT32 ui32DevIndex;
@@ -69,8 +111,9 @@ IMG_VOID* MatchDeviceKM_AnyVaCb(PVRSRV_DEVICE_NODE* psDeviceNode, va_list va)
        }
        else
        {
-               
-
+               /*this value will never be used, since the short circuit evaluation
+               of the first clause will stop because bIgnoreClass is true, but the
+               compiler complains if it's not initialized.*/
                eDevClass = PVRSRV_DEVICE_CLASS_FORCE_I32;
        }
 
@@ -82,6 +125,20 @@ IMG_VOID* MatchDeviceKM_AnyVaCb(PVRSRV_DEVICE_NODE* psDeviceNode, va_list va)
        return IMG_NULL;
 }
 
+/*!
+******************************************************************************
+
+ @Function     MatchPowerDeviceIndex_AnyVaCb
+
+ @Description
+                       Matches a power device with its device index.
+
+ @Input                va : variable argument list with:
+                               ui32DeviceIndex : device index
+
+ @Return       the pointer to the device it matched, IMG_NULL otherwise.
+
+******************************************************************************/
 IMG_VOID* MatchPowerDeviceIndex_AnyVaCb(PVRSRV_POWER_DEV *psPowerDev, va_list va)
 {
        IMG_UINT32 ui32DeviceIndex;
index 5b5d1ac..cccdd24 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          System memory functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    System memory allocation APIs
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
 #include "pvr_bridge_km.h"
@@ -47,7 +63,7 @@ FreeSharedSysMemCallBack(IMG_PVOID  pvParam,
                          sizeof(PVRSRV_KERNEL_MEM_INFO),
                          psKernelMemInfo,
                          IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        return PVRSRV_OK;
 }
@@ -80,6 +96,9 @@ PVRSRVAllocSharedSysMemoryKM(PVRSRV_PER_PROCESS_DATA  *psPerProc,
        if(OSAllocPages(psKernelMemInfo->ui32Flags,
                                        psKernelMemInfo->uAllocSize,
                                        (IMG_UINT32)HOST_PAGESIZE(),
+                                       IMG_NULL,
+                                       0,
+                                       IMG_NULL,
                                        &psKernelMemInfo->pvLinAddrKM,
                                        &psKernelMemInfo->sMemBlk.hOSMemHandle)
                != PVRSRV_OK)
@@ -92,7 +111,7 @@ PVRSRVAllocSharedSysMemoryKM(PVRSRV_PER_PROCESS_DATA *psPerProc,
                return PVRSRV_ERROR_OUT_OF_MEMORY;
        }
 
-       
+       /* register with the resman */
        psKernelMemInfo->sMemBlk.hResItem =
                                ResManRegisterRes(psPerProc->hResManContext,
                                                                  RESMAN_TYPE_SHARED_MEM_INFO,
@@ -151,3 +170,6 @@ PVRSRVDissociateMemFromResmanKM(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
        return eError;
 }
 
+/******************************************************************************
+ End of file (mem.c)
+******************************************************************************/
index e721fb3..04432b1 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Memory debugging routines.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Adds extra memory to the allocations to trace the memory bounds
+                and other runtime information.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef MEM_DEBUG_C
 #define MEM_DEBUG_C
@@ -39,13 +56,17 @@ extern "C"
 
 #define STOP_ON_ERROR 0
 
-       
-
-       
-
-
-
-
+       /*
+        Allocated Memory Layout:
+        
+        ---------                     \
+        Status    [OSMEM_DEBUG_INFO]   |- TEST_BUFFER_PADDING_STATUS
+        ---------                     <
+        [0xBB]*   [raw bytes]          |- ui32Size 
+        ---------                     <
+        [0xB2]*   [raw bytes]          |- TEST_BUFFER_PADDING_AFTER
+        ---------                     /
+       */
 
        IMG_BOOL MemCheck(const IMG_PVOID pvAddr, const IMG_UINT8 ui8Pattern, IMG_SIZE_T uSize)
        {
@@ -60,13 +81,14 @@ extern "C"
                return IMG_TRUE;
        }
 
-       
-
+       /*
+       This function expects the pointer to the user data, not the debug data.
+       */
        IMG_VOID OSCheckMemDebug(IMG_PVOID pvCpuVAddr, IMG_SIZE_T uSize, const IMG_CHAR *pszFileName, const IMG_UINT32 uLine)
        {
                OSMEM_DEBUG_INFO const *psInfo = (OSMEM_DEBUG_INFO *)((IMG_UINT32)pvCpuVAddr - TEST_BUFFER_PADDING_STATUS);
 
-               
+               /* invalid pointer */
                if (pvCpuVAddr == IMG_NULL)
                {
                        PVR_DPF((PVR_DBG_ERROR, "Pointer 0x%X : null pointer"
@@ -77,7 +99,7 @@ extern "C"
                        while (STOP_ON_ERROR);
                }
 
-               
+               /* align */
                if (((IMG_UINT32)pvCpuVAddr&3) != 0)
                {
                        PVR_DPF((PVR_DBG_ERROR, "Pointer 0x%X : invalid alignment"
@@ -88,7 +110,7 @@ extern "C"
                        while (STOP_ON_ERROR);
                }
 
-               
+               /*check guard region before*/
                if (!MemCheck((IMG_PVOID)psInfo->sGuardRegionBefore, 0xB1, sizeof(psInfo->sGuardRegionBefore)))
                {
                        PVR_DPF((PVR_DBG_ERROR, "Pointer 0x%X : guard region before overwritten"
@@ -99,7 +121,7 @@ extern "C"
                        while (STOP_ON_ERROR);
                }
 
-               
+               /*check size*/
                if (uSize != psInfo->uSize)
                {
                        PVR_DPF((PVR_DBG_WARNING, "Pointer 0x%X : supplied size was different to stored size (0x%X != 0x%X)"
@@ -110,7 +132,7 @@ extern "C"
                        while (STOP_ON_ERROR);
                }
 
-               
+               /*check size parity*/
                if ((0x01234567 ^ psInfo->uSizeParityCheck) != psInfo->uSize)
                {
                        PVR_DPF((PVR_DBG_WARNING, "Pointer 0x%X : stored size parity error (0x%X != 0x%X)"
@@ -122,11 +144,11 @@ extern "C"
                }
                else
                {
-                       
+                       /*the stored size is ok, so we use it instead the supplied uSize*/
                        uSize = psInfo->uSize;
                }
 
-               
+               /*check padding after*/
                if (uSize)
                {
                        if (!MemCheck((IMG_VOID*)((IMG_UINT32)pvCpuVAddr + uSize), 0xB2, TEST_BUFFER_PADDING_AFTER))
@@ -139,7 +161,7 @@ extern "C"
                        }
                }
 
-               
+               /* allocated... */
                if (psInfo->eValid != isAllocated)
                {
                        PVR_DPF((PVR_DBG_ERROR, "Pointer 0x%X : not allocated (freed? %d)"
@@ -155,7 +177,7 @@ extern "C"
        {
                IMG_SIZE_T i = 0;
 
-               for (; i < 128; i++) 
+               for (; i < 128; i++) /*changed to 128 to match the filename array size*/
                {
                        *pDest = *pSrc;
                        if (*pSrc == '\0') break;
@@ -187,11 +209,10 @@ extern "C"
                        return eError;
                }
 
-               
                OSMemSet((IMG_CHAR *)(*ppvCpuVAddr) + TEST_BUFFER_PADDING_STATUS, 0xBB, ui32Size);
                OSMemSet((IMG_CHAR *)(*ppvCpuVAddr) + ui32Size + TEST_BUFFER_PADDING_STATUS, 0xB2, TEST_BUFFER_PADDING_AFTER);
 
-               
+               /*fill the dbg info struct*/
                psInfo = (OSMEM_DEBUG_INFO *)(*ppvCpuVAddr);
 
                OSMemSet(psInfo->sGuardRegionBefore, 0xB1, sizeof(psInfo->sGuardRegionBefore));
@@ -201,11 +222,12 @@ extern "C"
                psInfo->uSize = ui32Size;
                psInfo->uSizeParityCheck = 0x01234567 ^ ui32Size;
 
-               
+               /*point to the user data section*/
                *ppvCpuVAddr = (IMG_PVOID) ((IMG_UINT32)*ppvCpuVAddr)+TEST_BUFFER_PADDING_STATUS;
 
 #ifdef PVRSRV_LOG_MEMORY_ALLOCS
-               
+               /*this is here to simplify the surounding logging macro, that is a expression
+               maybe the macro should be an expression */
                PVR_TRACE(("Allocated pointer (after debug info): 0x%X from %s:%d", *ppvCpuVAddr, pszFilename, ui32Line));
 #endif
 
@@ -221,16 +243,16 @@ extern "C"
        {
                OSMEM_DEBUG_INFO *psInfo;
 
-               
+               /*check dbginfo (arg pointing to user memory)*/
                OSCheckMemDebug(pvCpuVAddr, ui32Size, pszFilename, ui32Line);
 
-               
-               OSMemSet(pvCpuVAddr, 0xBF, ui32Size + TEST_BUFFER_PADDING_AFTER);  
+               /*mark memory as freed*/
+               OSMemSet(pvCpuVAddr, 0xBF, ui32Size + TEST_BUFFER_PADDING_AFTER);
 
-               
+               /*point to the starting address of the total allocated memory*/
                psInfo = (OSMEM_DEBUG_INFO *)((IMG_UINT32) pvCpuVAddr - TEST_BUFFER_PADDING_STATUS);
 
-               
+               /*update dbg info struct*/
                psInfo->uSize = 0;
                psInfo->uSizeParityCheck = 0;
                psInfo->eValid = isFree;
@@ -245,6 +267,6 @@ extern "C"
 }
 #endif
 
-#endif 
+#endif /* PVRSRV_DEBUG_OS_MEMORY */
 
-#endif        
+#endif /* MEM_DEBUG_C */
index 640eb04..7370ec1 100644 (file)
@@ -1,36 +1,53 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Time measuring functions.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
 #include "metrics.h"
 
+/* VGX: */
 #if defined(SUPPORT_VGX)
 #include "vgxapi_km.h"
 #endif
 
+/* SGX: */
 #if defined(SUPPORT_SGX)
 #include "sgxapi_km.h"
 #endif
@@ -47,6 +64,13 @@ static volatile IMG_UINT32 *pui32TimerRegister = 0;
 Temporal_Data asTimers[PVRSRV_NUM_TIMERS]; 
 
 
+/***********************************************************************************
+ Function Name      : PVRSRVTimeNow
+ Inputs             : None
+ Outputs            : None
+ Returns            : Current timer register value
+ Description        : Returns the current timer register value
+************************************************************************************/
 IMG_UINT32 PVRSRVTimeNow(IMG_VOID)
 {
        if (!pui32TimerRegister)
@@ -67,14 +91,21 @@ IMG_UINT32 PVRSRVTimeNow(IMG_VOID)
 
        return (0xffffffff-*pui32TimerRegister);
 
-#else 
+#else /* defined(__sh__) */
 
        return 0;
 
-#endif 
+#endif /* defined(__sh__) */
 }
 
 
+/***********************************************************************************
+ Function Name      : PVRSRVGetCPUFreq
+ Inputs             : None
+ Outputs            : None
+ Returns            : CPU timer frequency
+ Description        : Returns the CPU timer frequency
+************************************************************************************/
 static IMG_UINT32 PVRSRVGetCPUFreq(IMG_VOID)
 {
        IMG_UINT32 ui32Time1, ui32Time2;
@@ -91,6 +122,13 @@ static IMG_UINT32 PVRSRVGetCPUFreq(IMG_VOID)
 }
 
 
+/***********************************************************************************
+ Function Name      : PVRSRVSetupMetricTimers
+ Inputs             : pvDevInfo
+ Outputs            : None
+ Returns            : None
+ Description        : Resets metric timers and sets up the timer register
+************************************************************************************/
 IMG_VOID PVRSRVSetupMetricTimers(IMG_VOID *pvDevInfo)
 {
        IMG_UINT32 ui32Loop;
@@ -103,32 +141,37 @@ IMG_VOID PVRSRVSetupMetricTimers(IMG_VOID *pvDevInfo)
                asTimers[ui32Loop].ui32Count = 0;
        }
 
-
        #if defined(__sh__)
 
-               
-               
-               
-               
+               /* timer control register */
+               // clock / 1024 when TIMER_DIVISOR = 4
+               // underflow int disabled
+               // we get approx 38 uS per timer tick 
                *TCR_2 = TIMER_DIVISOR;
 
-               
+               /* reset the timer counter to 0 */
                *TCOR_2 = *TCNT_2 = (IMG_UINT)0xffffffff;
 
-               
+               /* start timer 2 */
                *TST_REG |= (IMG_UINT8)0x04;
 
                pui32TimerRegister = (IMG_UINT32 *)TCNT_2;
 
-       #else 
+       #else /* defined(__sh__) */
 
                pui32TimerRegister = 0;
 
-       #endif 
-
+       #endif /* defined(__sh__) */
 }
 
 
+/***********************************************************************************
+ Function Name      : PVRSRVOutputMetricTotals
+ Inputs             : None
+ Outputs            : None
+ Returns            : None
+ Description        : Displays final metric data
+************************************************************************************/
 IMG_VOID PVRSRVOutputMetricTotals(IMG_VOID)
 {
        IMG_UINT32 ui32TicksPerMS, ui32Loop;
@@ -149,12 +192,18 @@ IMG_VOID PVRSRVOutputMetricTotals(IMG_VOID)
                }
        }
 #if 0
-       
+       /*
+       ** EXAMPLE TIMER OUTPUT
+       */
        PVR_DPF((PVR_DBG_ERROR," Timer(%u): Total = %u",PVRSRV_TIMER_EXAMPLE_1, PVRSRV_TIMER_TOTAL_IN_TICKS(PVRSRV_TIMER_EXAMPLE_1)));
        PVR_DPF((PVR_DBG_ERROR," Timer(%u): Time = %ums",PVRSRV_TIMER_EXAMPLE_1, PVRSRV_TIMER_TOTAL_IN_MS(PVRSRV_TIMER_EXAMPLE_1)));
        PVR_DPF((PVR_DBG_ERROR," Timer(%u): Count = %u",PVRSRV_TIMER_EXAMPLE_1, PVRSRV_TIMER_COUNT(PVRSRV_TIMER_EXAMPLE_1)));
 #endif
 }
 
-#endif 
+#endif /* defined(DEBUG) || defined(TIMING) */
+
+/******************************************************************************
+ End of file (metrics.c)
+******************************************************************************/
 
index e0a46da..19ba9ea 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Wrapper layer for osfunc routines that have common code.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Adds extra memory to the allocations to trace the memory bounds
+                and other runtime information.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "img_types.h"
 #include "services_headers.h"
index 4d6c429..2d96dc3 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Common PDump functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if defined(PDUMP)
 #include <stdarg.h>
 #include "services_headers.h"
 #include "perproc.h"
 
+/* pdump headers */
 #include "pdump_km.h"
 #include "pdump_int.h"
 
+/* Allow temporary buffer size override */
 #if !defined(PDUMP_TEMP_BUFFER_SIZE)
 #define PDUMP_TEMP_BUFFER_SIZE (64 * 1024U)
 #endif
 
+/* DEBUG */
 #if 1
 #define PDUMP_DBG(a)   PDumpOSDebugPrintf (a)
 #else
@@ -53,6 +71,7 @@ static IMG_HANDLE ghTempBufferBlockAlloc;
 static IMG_UINT16 gui16MMUContextUsage = 0;
 
 #if defined(PDUMP_DEBUG_OUTFILES)
+/* counter increments each time debug write is called */
 IMG_UINT32 g_ui32EveryLineCounter = 1U;
 #endif
 
@@ -66,7 +85,7 @@ IMG_BOOL _PDumpIsPersistent(IMG_VOID)
 
        if(psPerProc == IMG_NULL)
        {
-               
+               /* only occurs early in driver init, and init phase is already persistent */
                return IMG_FALSE;
        }
        return psPerProc->bPDumpPersistent;
@@ -81,13 +100,15 @@ IMG_BOOL _PDumpIsProcessActive(IMG_VOID)
        PVRSRV_PER_PROCESS_DATA* psPerProc = PVRSRVFindPerProcessData();
        if(psPerProc == IMG_NULL)
        {
-               
+               /* FIXME: kernel process logs some comments when kernel module is
+                * loaded, want to keep those.
+                */
                return IMG_TRUE;
        }
        return psPerProc->bPDumpActive;
 }
 
-#endif 
+#endif /* SUPPORT_PDUMP_MULTI_PROCESS */
 
 #if defined(PDUMP_DEBUG_OUTFILES)
 static INLINE
@@ -96,16 +117,30 @@ IMG_UINT32 _PDumpGetPID(IMG_VOID)
        PVRSRV_PER_PROCESS_DATA* psPerProc = PVRSRVFindPerProcessData();
        if(psPerProc == IMG_NULL)
        {
-               
+               /* Kernel PID */
                return 0;
        }
        return psPerProc->ui32PID;
 }
-#endif 
-
+#endif /* PDUMP_DEBUG_OUTFILES */
+
+/**************************************************************************
+ * Function Name  : GetTempBuffer
+ * Inputs         : None
+ * Outputs        : None
+ * Returns        : Temporary buffer address, or IMG_NULL
+ * Description    : Get temporary buffer address.
+**************************************************************************/
 static IMG_VOID *GetTempBuffer(IMG_VOID)
 {
-       
+       /*
+        * Allocate the temporary buffer, it it hasn't been allocated already.
+        * Return the address of the temporary buffer, or IMG_NULL if it
+        * couldn't be allocated.
+        * It is expected that the buffer will be allocated once, at driver
+        * load time, and left in place until the driver unloads.
+        */
+
        if (gpvTempBuffer == IMG_NULL)
        {
                PVRSRV_ERROR eError = OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
@@ -144,19 +179,19 @@ static IMG_VOID FreeTempBuffer(IMG_VOID)
 
 IMG_VOID PDumpInitCommon(IMG_VOID)
 {
-       
+       /* Allocate temporary buffer for copying from user space */
        (IMG_VOID) GetTempBuffer();
 
-       
+       /* Call environment specific PDump initialisation */
        PDumpInit();
 }
 
 IMG_VOID PDumpDeInitCommon(IMG_VOID)
 {
-       
+       /* Free temporary buffer */
        FreeTempBuffer();
 
-       
+       /* Call environment specific PDump Deinitialisation */
        PDumpDeInit();
 }
 
@@ -191,6 +226,13 @@ PVRSRV_ERROR PDumpSetFrameKM(IMG_UINT32 ui32Frame)
 #endif
 }
 
+/**************************************************************************
+ * Function Name  : PDumpRegWithFlagsKM
+ * Inputs         : pszPDumpDevName, Register offset, and value to write
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Create a PDUMP string, which represents a register write
+**************************************************************************/
 PVRSRV_ERROR PDumpRegWithFlagsKM(IMG_CHAR *pszPDumpRegName,
                                                                IMG_UINT32 ui32Reg,
                                                                IMG_UINT32 ui32Data,
@@ -211,6 +253,13 @@ PVRSRV_ERROR PDumpRegWithFlagsKM(IMG_CHAR *pszPDumpRegName,
        return PVRSRV_OK;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpRegKM
+ * Inputs         : Register offset, and value to write
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Create a PDUMP string, which represents a register write
+**************************************************************************/
 PVRSRV_ERROR PDumpRegKM(IMG_CHAR *pszPDumpRegName,
                                                IMG_UINT32 ui32Reg,
                                                IMG_UINT32 ui32Data)
@@ -218,6 +267,18 @@ PVRSRV_ERROR PDumpRegKM(IMG_CHAR *pszPDumpRegName,
        return PDumpRegWithFlagsKM(pszPDumpRegName, ui32Reg, ui32Data, PDUMP_FLAGS_CONTINUOUS);
 }
 
+/**************************************************************************
+ * Function Name  : PDumpRegPolWithFlagsKM
+ * Inputs         : Description of what this register read is trying to do
+ *                                     pszPDumpDevName
+ *                                     Register offset
+ *                                     expected value
+ *                                     mask for that value
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Create a PDUMP string which represents a register read
+ *                                     with the expected value
+**************************************************************************/
 PVRSRV_ERROR PDumpRegPolWithFlagsKM(IMG_CHAR *pszPDumpRegName,
                                                                        IMG_UINT32 ui32RegAddr, 
                                                                        IMG_UINT32 ui32RegValue, 
@@ -225,7 +286,7 @@ PVRSRV_ERROR PDumpRegPolWithFlagsKM(IMG_CHAR *pszPDumpRegName,
                                                                        IMG_UINT32 ui32Flags,
                                                                        PDUMP_POLL_OPERATOR     eOperator)
 {
-       
+       /* Timings correct for linux and XP */
        #define POLL_DELAY                      1000U
        #define POLL_COUNT_LONG         (2000000000U / POLL_DELAY)
        #define POLL_COUNT_SHORT        (1000000U / POLL_DELAY)
@@ -237,25 +298,11 @@ PVRSRV_ERROR PDumpRegPolWithFlagsKM(IMG_CHAR *pszPDumpRegName,
        PDUMP_DBG(("PDumpRegPolWithFlagsKM"));
        if ( _PDumpIsPersistent() )
        {
-               
+               /* Don't pdump-poll if the process is persistent */
                return PVRSRV_OK;
        }
 
-#if 0
-       if (((ui32RegAddr == EUR_CR_EVENT_STATUS) &&
-               (ui32RegValue & ui32Mask & EUR_CR_EVENT_STATUS_TA_FINISHED_MASK) != 0) ||
-           ((ui32RegAddr == EUR_CR_EVENT_STATUS) &&
-               (ui32RegValue & ui32Mask & EUR_CR_EVENT_STATUS_PIXELBE_END_RENDER_MASK) != 0) ||
-           ((ui32RegAddr == EUR_CR_EVENT_STATUS) &&
-               (ui32RegValue & ui32Mask & EUR_CR_EVENT_STATUS_DPM_3D_MEM_FREE_MASK) != 0))
-       {
-               ui32PollCount = POLL_COUNT_LONG;
-       }
-       else
-#endif
-       {
-               ui32PollCount = POLL_COUNT_LONG;
-       }
+       ui32PollCount = POLL_COUNT_LONG;
 
        eErr = PDumpOSBufprintf(hScript, ui32MaxLen, "POL :%s:0x%08X 0x%08X 0x%08X %d %u %d\r\n",
                                                        pszPDumpRegName, ui32RegAddr, ui32RegValue,
@@ -270,11 +317,38 @@ PVRSRV_ERROR PDumpRegPolWithFlagsKM(IMG_CHAR *pszPDumpRegName,
 }
 
 
+/**************************************************************************
+ * Function Name  : PDumpRegPol
+ * Inputs         : Description of what this register read is trying to do
+ *                                     pszPDumpDevName
+                                       Register offset
+ *                                     expected value
+ *                                     mask for that value
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Create a PDUMP string which represents a register read
+ *                                     with the expected value
+**************************************************************************/
 PVRSRV_ERROR PDumpRegPolKM(IMG_CHAR *pszPDumpRegName, IMG_UINT32 ui32RegAddr, IMG_UINT32 ui32RegValue, IMG_UINT32 ui32Mask, PDUMP_POLL_OPERATOR        eOperator)
 {
        return PDumpRegPolWithFlagsKM(pszPDumpRegName, ui32RegAddr, ui32RegValue, ui32Mask, PDUMP_FLAGS_CONTINUOUS, eOperator);
 }
 
+/**************************************************************************
+ * Function Name  : PDumpMallocPages
+ * Inputs         : psDevID, ui32DevVAddr, pvLinAddr, ui32NumBytes, hOSMemHandle
+ *                : hUniqueTag
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Malloc memory pages
+
+FIXME: This function assumes pvLinAddr is the address of the start of the 
+block for this hOSMemHandle.
+If this isn't true, the call to PDumpOSCPUVAddrToDevPAddr below will be 
+incorrect.  (Consider using OSMemHandleToCPUPAddr() instead?)
+The only caller at the moment is in buffer_manager.c, which does the right
+thing.
+**************************************************************************/
 PVRSRV_ERROR PDumpMallocPages (PVRSRV_DEVICE_IDENTIFIER        *psDevID,
                            IMG_UINT32         ui32DevVAddr,
                            IMG_CPU_VIRTADDR   pvLinAddr,
@@ -294,14 +368,14 @@ PVRSRV_ERROR PDumpMallocPages (PVRSRV_DEVICE_IDENTIFIER   *psDevID,
 
        PDUMP_GET_SCRIPT_STRING();
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-       
+       /* Always dump physical pages backing a shared allocation */
        ui32Flags |= ( _PDumpIsPersistent() || bShared ) ? PDUMP_FLAGS_PERSISTENT : 0;
 #else
        PVR_UNREFERENCED_PARAMETER(bShared);
        ui32Flags |= ( _PDumpIsPersistent() ) ? PDUMP_FLAGS_PERSISTENT : 0;
 #endif
 
-       
+       /* However, lin addr is only required in non-linux OSes */
 #if !defined(LINUX)
        PVR_ASSERT(((IMG_UINTPTR_T)pvLinAddr & HOST_PAGEMASK) == 0);
 #endif
@@ -309,8 +383,9 @@ PVRSRV_ERROR PDumpMallocPages (PVRSRV_DEVICE_IDENTIFIER     *psDevID,
        PVR_ASSERT(((IMG_UINT32) ui32DevVAddr & HOST_PAGEMASK) == 0);
        PVR_ASSERT(((IMG_UINT32) ui32NumBytes & HOST_PAGEMASK) == 0);
 
-       
-
+       /*
+               Write a comment to the PDump2 script streams indicating the memory allocation
+       */
        eErr = PDumpOSBufprintf(hScript, ui32MaxLen, "-- MALLOC :%s:VA_%08X 0x%08X %u\r\n",
                        psDevID->pszPDumpDevName, ui32DevVAddr, ui32NumBytes, ui32PageSize);
        if(eErr != PVRSRV_OK)
@@ -319,8 +394,9 @@ PVRSRV_ERROR PDumpMallocPages (PVRSRV_DEVICE_IDENTIFIER     *psDevID,
        }
        PDumpOSWriteString2(hScript, ui32Flags);
 
-       
-
+       /*
+               Write to the MMU script stream indicating the memory allocation
+       */
        pui8LinAddr = (IMG_PUINT8) pvLinAddr;
        ui32Offset = 0;
        ui32NumPages = ui32NumBytes / ui32PageSize;
@@ -328,16 +404,11 @@ PVRSRV_ERROR PDumpMallocPages (PVRSRV_DEVICE_IDENTIFIER   *psDevID,
        { 
                ui32NumPages--;
 
-               
-
-
-
-
-
-
-               
-               
-               
+               /* See FIXME in function header. 
+                * Currently:  linux pdump uses OSMemHandle and Offset 
+                *             other OSes use the LinAddr. 
+                */
+               /* Calculate the device physical address for this page */
                PDumpOSCPUVAddrToDevPAddr(psDevID->eDeviceType,
                                hOSMemHandle,
                                ui32Offset,
@@ -345,7 +416,7 @@ PVRSRV_ERROR PDumpMallocPages (PVRSRV_DEVICE_IDENTIFIER     *psDevID,
                                ui32PageSize,
                                &sDevPAddr);
                ui32Page = (IMG_UINT32)(sDevPAddr.uiAddr / ui32PageSize);
-               
+               /* increment kernel virtual address */
                pui8LinAddr     += ui32PageSize;
                ui32Offset += ui32PageSize;
 
@@ -366,6 +437,13 @@ PVRSRV_ERROR PDumpMallocPages (PVRSRV_DEVICE_IDENTIFIER    *psDevID,
 }
 
 
+/**************************************************************************
+ * Function Name  : PDumpMallocPageTable
+ * Inputs         : psDevId, pvLinAddr, ui32NumBytes, hUniqueTag
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Malloc memory page table
+**************************************************************************/
 PVRSRV_ERROR PDumpMallocPageTable (PVRSRV_DEVICE_IDENTIFIER    *psDevId,
                                                                   IMG_HANDLE hOSMemHandle,
                                                                   IMG_UINT32 ui32Offset,
@@ -383,8 +461,9 @@ PVRSRV_ERROR PDumpMallocPageTable (PVRSRV_DEVICE_IDENTIFIER *psDevId,
        ui32Flags |= PDUMP_FLAGS_CONTINUOUS;
        ui32Flags |= ( _PDumpIsPersistent() ) ? PDUMP_FLAGS_PERSISTENT : 0;
        
-       
-
+       /*
+               Write a comment to the PDump2 script streams indicating the memory allocation
+       */
        eErr = PDumpOSBufprintf(hScript,
                                                        ui32MaxLen,
                                                        "-- MALLOC :%s:PAGE_TABLE 0x%08X %u\r\n",
@@ -397,15 +476,16 @@ PVRSRV_ERROR PDumpMallocPageTable (PVRSRV_DEVICE_IDENTIFIER       *psDevId,
        }
        PDumpOSWriteString2(hScript, ui32Flags);
 
-       
-
-       
-       
-       
-       
+       /*
+               Write to the MMU script stream indicating the memory allocation
+       */
+       // FIXME: we'll never need more than a 4k page for a pagetable
+       // fixing to 1 page for now.
+       // note: when the mmu code supports packed pagetables the PTs
+       // will be as small as 16bytes
 
        PDumpOSCPUVAddrToDevPAddr(psDevId->eDeviceType,
-                       hOSMemHandle, 
+                       hOSMemHandle, /* um - does this mean the pvLinAddr would be ignored?  Is that safe? */
                        ui32Offset,
                        (IMG_PUINT8) pvLinAddr,
                        ui32PTSize,
@@ -415,8 +495,8 @@ PVRSRV_ERROR PDumpMallocPageTable (PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                                                        psDevId->pszPDumpDevName,
                                                                                        (IMG_UINT32)(IMG_UINTPTR_T)hUniqueTag,
                                                                                        sDevPAddr.uiAddr,
-                                                                                       ui32PTSize,
-                                                                                       ui32PTSize,
+                                                                                       ui32PTSize,//size
+                                                                                       ui32PTSize,//alignment
                                                                                        sDevPAddr.uiAddr);
        if(eErr != PVRSRV_OK)
        {
@@ -427,12 +507,21 @@ PVRSRV_ERROR PDumpMallocPageTable (PVRSRV_DEVICE_IDENTIFIER       *psDevId,
        return PVRSRV_OK;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpFreePages
+ * Inputs         : psBMHeap, sDevVAddr, ui32NumBytes, hUniqueTag,
+                                       bInterLeaved
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Free memory pages
+**************************************************************************/
 PVRSRV_ERROR PDumpFreePages    (BM_HEAP                        *psBMHeap,
                          IMG_DEV_VIRTADDR  sDevVAddr,
                          IMG_UINT32        ui32NumBytes,
                          IMG_UINT32        ui32PageSize,
                          IMG_HANDLE        hUniqueTag,
-                                                IMG_BOOL                  bInterleaved)
+                                                IMG_BOOL                  bInterleaved,
+                                                IMG_BOOL                  bSparse)
 {
        PVRSRV_ERROR eErr;
        IMG_UINT32 ui32NumPages, ui32PageCounter;
@@ -448,8 +537,9 @@ PVRSRV_ERROR PDumpFreePages (BM_HEAP                        *psBMHeap,
        psDeviceNode = psBMHeap->pBMContext->psDeviceNode;
        ui32Flags |= ( _PDumpIsPersistent() ) ? PDUMP_FLAGS_PERSISTENT : 0;
 
-       
-
+       /*
+               Write a comment to the PDUMP2 script streams indicating the memory free
+       */
        eErr = PDumpOSBufprintf(hScript, ui32MaxLen, "-- FREE :%s:VA_%08X\r\n", 
                                                        psDeviceNode->sDevId.pszPDumpDevName, sDevVAddr.uiAddr);
        if(eErr != PVRSRV_OK)
@@ -458,7 +548,9 @@ PVRSRV_ERROR PDumpFreePages (BM_HEAP                        *psBMHeap,
        }
 
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-       
+       /* if we're dumping a shared heap, need to ensure phys allocation
+        * is freed even if this app isn't the one marked for pdumping
+        */
        {
                PVRSRV_DEVICE_NODE *psDeviceNode = psBMHeap->pBMContext->psDeviceNode;
                
@@ -470,8 +562,9 @@ PVRSRV_ERROR PDumpFreePages (BM_HEAP                        *psBMHeap,
 #endif
        PDumpOSWriteString2(hScript, ui32Flags);
 
-       
-
+       /*
+               Write to the MMU script stream indicating the memory free
+       */
        ui32NumPages = ui32NumBytes / ui32PageSize;
        for (ui32PageCounter = 0; ui32PageCounter < ui32NumPages; ui32PageCounter++)
        {
@@ -479,7 +572,13 @@ PVRSRV_ERROR PDumpFreePages        (BM_HEAP                        *psBMHeap,
                {
                        sDevPAddr = psDeviceNode->pfnMMUGetPhysPageAddr(psBMHeap->pMMUHeap, sDevVAddr);
 
-                       PVR_ASSERT(sDevPAddr.uiAddr != 0)
+                       /* With sparse mappings we expect spaces */
+                       if (bSparse && (sDevPAddr.uiAddr == 0))
+                       {
+                               continue;
+                       }
+
+                       PVR_ASSERT(sDevPAddr.uiAddr != 0);
 
                        eErr = PDumpOSBufprintf(hScript, ui32MaxLen, "FREE :%s:PA_%08X%08X\r\n",
                                                                        psDeviceNode->sDevId.pszPDumpDevName, (IMG_UINT32)(IMG_UINTPTR_T)hUniqueTag, sDevPAddr.uiAddr);
@@ -491,7 +590,7 @@ PVRSRV_ERROR PDumpFreePages (BM_HEAP                        *psBMHeap,
                }
                else
                {
-                       
+                       /* Gap pages in an interleaved allocation should be ignored. */
                }
 
                sDevVAddr.uiAddr += ui32PageSize;
@@ -499,6 +598,13 @@ PVRSRV_ERROR PDumpFreePages        (BM_HEAP                        *psBMHeap,
        return PVRSRV_OK;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpFreePageTable
+ * Inputs         : psDevID, pvLinAddr, ui32NumBytes, hUniqueTag
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Free memory page table
+**************************************************************************/
 PVRSRV_ERROR PDumpFreePageTable        (PVRSRV_DEVICE_IDENTIFIER *psDevID,
                                                                 IMG_HANDLE hOSMemHandle,
                                                                 IMG_CPU_VIRTADDR   pvLinAddr,
@@ -515,11 +621,12 @@ PVRSRV_ERROR PDumpFreePageTable   (PVRSRV_DEVICE_IDENTIFIER *psDevID,
        ui32Flags |= PDUMP_FLAGS_CONTINUOUS;
        ui32Flags |= ( _PDumpIsPersistent() ) ? PDUMP_FLAGS_PERSISTENT : 0;
 
-       
-       PVR_ASSERT(((IMG_UINTPTR_T)pvLinAddr & (ui32PTSize-1UL)) == 0); 
-
-       
+       /* override QAC warning about wrap around */
+       PVR_ASSERT(((IMG_UINTPTR_T)pvLinAddr & (ui32PTSize-1UL)) == 0); /* PRQA S 3382 */
 
+       /*
+               Write a comment to the PDUMP2 script streams indicating the memory free
+       */
        eErr = PDumpOSBufprintf(hScript, ui32MaxLen, "-- FREE :%s:PAGE_TABLE\r\n", psDevID->pszPDumpDevName);
        if(eErr != PVRSRV_OK)
        {
@@ -527,15 +634,16 @@ PVRSRV_ERROR PDumpFreePageTable   (PVRSRV_DEVICE_IDENTIFIER *psDevID,
        }
        PDumpOSWriteString2(hScript, ui32Flags);
 
-       
-
-       
-       
-       
-       
+       /*
+               Write to the MMU script stream indicating the memory free
+       */
+       // FIXME: we'll never need more than a 4k page for a pagetable
+       // fixing to 1 page for now.
+       // note: when the mmu code supports packed pagetables the PTs
+       // will be as small as 16bytes
 
        PDumpOSCPUVAddrToDevPAddr(psDevID->eDeviceType,
-                                                         hOSMemHandle, 
+                                                         hOSMemHandle, /* um - does this mean the pvLinAddr would be ignored?  Is that safe? */
                        0,
                        (IMG_PUINT8) pvLinAddr,
                        ui32PTSize,
@@ -556,6 +664,18 @@ PVRSRV_ERROR PDumpFreePageTable    (PVRSRV_DEVICE_IDENTIFIER *psDevID,
        return PVRSRV_OK;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpPDRegWithFlags
+ * Inputs         : psMMUAttrib
+ *                               : ui32Reg
+ *                               : ui32Data
+ *                               : hUniqueTag
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Kernel Services internal pdump memory API
+ *                                     Used for registers specifying physical addresses
+                                       e.g. MMU page directory register
+**************************************************************************/
 PVRSRV_ERROR PDumpPDRegWithFlags(PDUMP_MMU_ATTRIB *psMMUAttrib,
                                                        IMG_UINT32 ui32Reg,
                                                         IMG_UINT32 ui32Data,
@@ -575,8 +695,9 @@ PVRSRV_ERROR PDumpPDRegWithFlags(PDUMP_MMU_ATTRIB *psMMUAttrib,
                pszRegString = psMMUAttrib->sDevId.pszPDumpRegName;
        }
 
-       
-
+       /*
+               Write to the MMU script stream indicating the physical page directory
+       */
 #if defined(SGX_FEATURE_36BIT_MMU)
        eErr = PDumpOSBufprintf(hScript, ui32MaxLen,
                         "WRW :%s:$1 :%s:PA_%08X%08X:0x0\r\n",
@@ -626,6 +747,18 @@ PVRSRV_ERROR PDumpPDRegWithFlags(PDUMP_MMU_ATTRIB *psMMUAttrib,
        return PVRSRV_OK;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpPDReg
+ * Inputs         : psMMUAttrib
+                                 : ui32Reg
+ *                               : ui32Data
+ *                               : hUniqueTag
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Kernel Services internal pdump memory API
+ *                                     Used for registers specifying physical addresses
+                                       e.g. MMU page directory register
+**************************************************************************/
 PVRSRV_ERROR PDumpPDReg        (PDUMP_MMU_ATTRIB *psMMUAttrib, 
                                         IMG_UINT32 ui32Reg,
                                         IMG_UINT32 ui32Data,
@@ -634,6 +767,19 @@ PVRSRV_ERROR PDumpPDReg    (PDUMP_MMU_ATTRIB *psMMUAttrib,
        return PDumpPDRegWithFlags(psMMUAttrib, ui32Reg, ui32Data, PDUMP_FLAGS_CONTINUOUS, hUniqueTag);
 }
 
+/**************************************************************************
+ * Function Name  : PDumpMemPolKM
+ * Inputs         : psMemInfo
+ *                               : ui32Offset
+ *                               : ui32Value
+ *                               : ui32Mask
+ *                               : eOperator
+ *                               : ui32Flags
+ *                               : hUniqueTag
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Implements Client pdump memory poll API
+**************************************************************************/
 PVRSRV_ERROR PDumpMemPolKM(PVRSRV_KERNEL_MEM_INFO              *psMemInfo,
                                                   IMG_UINT32                   ui32Offset,
                                                   IMG_UINT32                   ui32Value,
@@ -661,17 +807,18 @@ PVRSRV_ERROR PDumpMemPolKM(PVRSRV_KERNEL_MEM_INFO         *psMemInfo,
 
        if ( _PDumpIsPersistent() )
        {
-               
+               /* Don't pdump-poll if the process is persistent */
                return PVRSRV_OK;
        }
 
-       
+       /* Check the offset and size don't exceed the bounds of the allocation */
        PVR_ASSERT((ui32Offset + sizeof(IMG_UINT32)) <= psMemInfo->uAllocSize);
 
        psMMUAttrib = ((BM_BUF*)psMemInfo->sMemBlk.hBuffer)->pMapping->pBMHeap->psMMUAttrib;
 
-       
-
+       /*
+               Write a comment to the PDump2 script streams indicating the virtual memory pol
+       */
        eErr = PDumpOSBufprintf(hScript,
                         ui32MaxLen,
                         "-- POL :%s:VA_%08X 0x%08X 0x%08X %d %d %d\r\n",
@@ -691,27 +838,28 @@ PVRSRV_ERROR PDumpMemPolKM(PVRSRV_KERNEL_MEM_INFO         *psMemInfo,
 
        pui8LinAddr = psMemInfo->pvLinAddrKM;
 
-       
+       /* Advance address by offset */
        pui8LinAddr += ui32Offset;
 
-       
-
-
+       /*
+               query the buffer manager for the physical pages that back the
+               virtual address
+       */
        PDumpOSCPUVAddrToPhysPages(psMemInfo->sMemBlk.hOSMemHandle,
                        ui32Offset,
                        pui8LinAddr,
                        psMMUAttrib->ui32DataPageMask,
                        &ui32PageOffset);
 
-       
+       /* calculate the DevV page address */
        sDevVPageAddr.uiAddr = psMemInfo->sDevVAddr.uiAddr + ui32Offset - ui32PageOffset;
 
        PVR_ASSERT((sDevVPageAddr.uiAddr & psMMUAttrib->ui32DataPageMask) == 0);
 
-       
+       /* get the physical page address based on the device virtual address */
        BM_GetPhysPageAddr(psMemInfo, sDevVPageAddr, &sDevPAddr);
 
-       
+       /* convert DevP page address to byte address */
        sDevPAddr.uiAddr += ui32PageOffset;
 
        eErr = PDumpOSBufprintf(hScript,
@@ -735,12 +883,23 @@ PVRSRV_ERROR PDumpMemPolKM(PVRSRV_KERNEL_MEM_INFO         *psMemInfo,
        return PVRSRV_OK;
 }
 
-PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
-                                               PVRSRV_KERNEL_MEM_INFO *psMemInfo,
-                                               IMG_UINT32 ui32Offset,
-                                               IMG_UINT32 ui32Bytes,
-                                               IMG_UINT32 ui32Flags,
-                                               IMG_HANDLE hUniqueTag)
+/**************************************************************************
+ * Function Name  : _PDumpMemIntKM
+ * Inputs         : psMemInfo
+ *                               : ui32Offset
+ *                               : ui32Bytes
+ *                               : ui32Flags
+ *                               : hUniqueTag
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Implements Client pdump mem API
+**************************************************************************/
+static PVRSRV_ERROR _PDumpMemIntKM(IMG_PVOID pvAltLinAddr,
+                                                                  PVRSRV_KERNEL_MEM_INFO *psMemInfo,
+                                                                  IMG_UINT32 ui32Offset,
+                                                                  IMG_UINT32 ui32Bytes,
+                                                                  IMG_UINT32 ui32Flags,
+                                                                  IMG_HANDLE hUniqueTag)
 {
        PVRSRV_ERROR eErr;
        IMG_UINT32 ui32NumPages;
@@ -757,7 +916,7 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
 
        PDUMP_GET_SCRIPT_AND_FILE_STRING();
        
-        
+       /* PRQA S 3415 1 */ /* side effects desired */
        if (ui32Bytes == 0 || PDumpOSIsSuspended())
        {
                return PVRSRV_OK;
@@ -765,8 +924,9 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
 
        psMMUAttrib = ((BM_BUF*)psMemInfo->sMemBlk.hBuffer)->pMapping->pBMHeap->psMMUAttrib;
        
-       
-
+       /*
+               check the offset and size don't exceed the bounds of the allocation
+       */
        PVR_ASSERT((ui32Offset + ui32Bytes) <= psMemInfo->uAllocSize);
 
        if (!PDumpOSJTInitialised())
@@ -775,7 +935,9 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
        }
 
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-       
+       /* if we're dumping a shared heap, need to ensure phys allocation
+        * is initialised even if this app isn't the one marked for pdumping
+        */
        {
                BM_HEAP *pHeap = ((BM_BUF*)psMemInfo->sMemBlk.hBuffer)->pMapping->pBMHeap;
                PVRSRV_DEVICE_NODE *psDeviceNode = pHeap->pBMContext->psDeviceNode;
@@ -787,7 +949,7 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
        }
 #endif
 
-       
+       /* setup memory addresses */
        if(pvAltLinAddr)
        {
                pui8DataLinAddr = pvAltLinAddr;
@@ -799,7 +961,7 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
        pui8LinAddr = (IMG_UINT8 *)psMemInfo->pvLinAddrKM;
        sDevVAddr = psMemInfo->sDevVAddr;
 
-       
+       /* advance address by offset */
        sDevVAddr.uiAddr += ui32Offset;
        pui8LinAddr += ui32Offset;
 
@@ -809,8 +971,9 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
 
        ui32ParamOutPos = PDumpOSGetStreamOffset(PDUMP_STREAM_PARAM2);
 
-       
-
+       /*
+               write the binary data up-front.
+       */
        if(!PDumpOSWriteString(PDumpOSGetStream(PDUMP_STREAM_PARAM2),
                                                pui8DataLinAddr,
                                                ui32Bytes,
@@ -832,8 +995,9 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
                return eErr;
        }
 
-       
-
+       /*
+               Write a comment to the PDump2 script streams indicating the virtual memory load
+       */
        eErr = PDumpOSBufprintf(hScript,
                         ui32MaxLenScript,
                         "-- LDB :%s:VA_%08X%08X:0x%08X 0x%08X 0x%08X %s\r\n",
@@ -850,9 +1014,10 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
        }
        PDumpOSWriteString2(hScript, ui32Flags);
 
-       
-
-
+       /*
+               query the buffer manager for the physical pages that back the
+               virtual address
+       */
        PDumpOSCPUVAddrToPhysPages(psMemInfo->sMemBlk.hOSMemHandle,
                        ui32Offset,
                        pui8LinAddr,
@@ -865,30 +1030,30 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
        {
                ui32NumPages--;
        
-               
+               /* calculate the DevV page address */
                sDevVPageAddr.uiAddr = sDevVAddr.uiAddr - ui32PageByteOffset;
 
                if (ui32DataPageSize <= PDUMP_TEMP_BUFFER_SIZE)
                {
-                       
+                       /* if a page fits within temp buffer, we should dump in page-aligned chunks. */
                        PVR_ASSERT((sDevVPageAddr.uiAddr & psMMUAttrib->ui32DataPageMask) == 0);
                }
 
-               
+               /* get the physical page address based on the device virtual address */
                BM_GetPhysPageAddr(psMemInfo, sDevVPageAddr, &sDevPAddr);
 
-               
+               /* convert DevP page address to byte address */
                sDevPAddr.uiAddr += ui32PageByteOffset;
 
-               
+               /* how many bytes to dump from this page */
                if (ui32PageByteOffset + ui32Bytes > ui32DataPageSize)
                {
-                       
+                       /* dump up to the page boundary */
                        ui32BlockBytes = ui32DataPageSize - ui32PageByteOffset;
                }
                else
                {
-                       
+                       /* dump what's left */
                        ui32BlockBytes = ui32Bytes;
                }
 
@@ -908,28 +1073,68 @@ PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
                }
                PDumpOSWriteString2(hScript, ui32Flags);
 
-               
+               /* update details for next page */
 
 #if defined(SGX_FEATURE_VARIABLE_MMU_PAGE_SIZE)
-               
+               /* page may be larger than pdump temporary buffer */
                ui32PageByteOffset = (ui32PageByteOffset + ui32BlockBytes) % ui32DataPageSize;
 #else
-               
+               /* page offset 0 after first page dump */
                ui32PageByteOffset = 0;
 #endif
-               
-               ui32Bytes -= ui32BlockBytes;     
-               
+               /* bytes left over */
+               ui32Bytes -= ui32BlockBytes;    /* PRQA S 3382 */ /* QAC missed MIN test */
+               /* advance devVaddr */
                sDevVAddr.uiAddr += ui32BlockBytes;
-               
+               /* advance the cpuVaddr */
                pui8LinAddr += ui32BlockBytes;
-               
+               /* update the file write offset */
                ui32ParamOutPos += ui32BlockBytes;
        }
 
        return PVRSRV_OK;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpMemKM
+ * Inputs         : psMemInfo
+ *                               : ui32Offset
+ *                               : ui32Bytes
+ *                               : ui32Flags
+ *                               : hUniqueTag
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Implements Client pdump mem API
+**************************************************************************/
+PVRSRV_ERROR PDumpMemKM(IMG_PVOID pvAltLinAddr,
+                                               PVRSRV_KERNEL_MEM_INFO *psMemInfo,
+                                               IMG_UINT32 ui32Offset,
+                                               IMG_UINT32 ui32Bytes,
+                                               IMG_UINT32 ui32Flags,
+                                               IMG_HANDLE hUniqueTag)
+{
+       /*
+               For now we don't support dumping sparse allocations that
+               are from within the kernel, or are from UM but without a
+               alternative linear address
+       */
+       PVR_ASSERT((psMemInfo->ui32Flags & PVRSRV_MEM_SPARSE) == 0);
+
+       if (psMemInfo->ui32Flags & PVRSRV_MEM_SPARSE)
+       {
+               return PVRSRV_ERROR_INVALID_PARAMS;
+       }
+       else
+       {
+               return _PDumpMemIntKM(pvAltLinAddr,
+                                                         psMemInfo,
+                                                         ui32Offset,
+                                                         ui32Bytes,
+                                                         ui32Flags,
+                                                         hUniqueTag);
+       }
+}
+
 PVRSRV_ERROR PDumpMemPDEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
                                                                 IMG_HANDLE hOSMemHandle,
                                                                 IMG_CPU_VIRTADDR pvLinAddr,
@@ -941,7 +1146,7 @@ PVRSRV_ERROR PDumpMemPDEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
 {
        PDUMP_MMU_ATTRIB sMMUAttrib;
        
-       
+       /* Override the (variable) PT size since PDs are always 4K in size */
        sMMUAttrib = *psMMUAttrib;
        sMMUAttrib.ui32PTSize = (IMG_UINT32)HOST_PAGESIZE();
        return PDumpMemPTEntriesKM(     &sMMUAttrib,
@@ -954,6 +1159,23 @@ PVRSRV_ERROR PDumpMemPDEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
                                                                hUniqueTag2);
 }
 
+/**************************************************************************
+ * Function Name  : PDumpMemPTEntriesKM
+ * Inputs         : psMMUAttrib - MMU attributes for pdump
+ *                               : pvLinAddr - CPU address of PT base
+ *                               : ui32Bytes - size
+ *                               : ui32Flags - pdump flags
+ *                               : bInitialisePages - whether to initialise pages from file
+ *                               : hUniqueTag1 - ID for PT physical page
+ *                               : hUniqueTag2 - ID for target physical page (if !bInitialisePages)
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Kernel Services internal pdump memory API
+ *                                     Used for memory without DevVAddress mappings
+                                       e.g. MMU page tables
+                                       FIXME: This function doesn't support non-4k data pages,
+                                       e.g. dummy data page
+**************************************************************************/
 PVRSRV_ERROR PDumpMemPTEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
                                                                 IMG_HANDLE hOSMemHandle,
                                                                 IMG_CPU_VIRTADDR pvLinAddr,
@@ -972,7 +1194,7 @@ PVRSRV_ERROR PDumpMemPTEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
        IMG_CPU_PHYADDR sCpuPAddr;
        IMG_UINT32 ui32Offset;
        IMG_UINT32 ui32ParamOutPos;
-       IMG_UINT32 ui32PageMask; 
+       IMG_UINT32 ui32PageMask; /* mask for the physical page backing the PT */
 
        PDUMP_GET_SCRIPT_AND_FILE_STRING();
        ui32Flags |= ( _PDumpIsPersistent() ) ? PDUMP_FLAGS_PERSISTENT : 0;
@@ -998,9 +1220,10 @@ PVRSRV_ERROR PDumpMemPTEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
 
        if (bInitialisePages)
        {
-               
-
-
+               /*
+                       write the binary data up-front
+                       Use the 'continuous' memory stream
+               */
                if (!PDumpOSWriteString(PDumpOSGetStream(PDUMP_STREAM_PARAM2),
                                                        pvLinAddr,
                                                        ui32Bytes,
@@ -1023,16 +1246,18 @@ PVRSRV_ERROR PDumpMemPTEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
                }
        }
 
-       
-
-
-
-
+       /*
+               Mask for the physical page address backing the PT
+               The PT size can be less than 4k with variable page size support
+               The PD size is always 4k
+               FIXME: This won't work for dumping the dummy data page
+       */
        ui32PageMask = psMMUAttrib->ui32PTSize - 1;
 
-       
-
-       
+       /*
+               Write to the MMU script stream indicating the physical page table entries
+       */
+       /* physical pages that back the virtual address */
        ui32PageOffset  = (IMG_UINT32)((IMG_UINTPTR_T)pvLinAddr & (psMMUAttrib->ui32PTSize - 1));
        ui32NumPages    = (ui32PageOffset + ui32Bytes + psMMUAttrib->ui32PTSize - 1) / psMMUAttrib->ui32PTSize;
        pui8LinAddr             = (IMG_UINT8*) pvLinAddr;
@@ -1040,29 +1265,31 @@ PVRSRV_ERROR PDumpMemPTEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
        while (ui32NumPages)
        {
                ui32NumPages--;
-               
-
-
-
-
-
+               /* FIXME: if we used OSMemHandleToCPUPAddr() here, we might be
+                  able to lose the lin addr arg.  At least one thing that
+                  would need to be done here is to pass in an offset, as the
+                  calling function doesn't necessarily give us the lin addr
+                  of the start of the mem area.  Probably best to keep the
+                  lin addr arg for now - but would be nice to remove the
+                  redundancy */
                sCpuPAddr = OSMapLinToCPUPhys(hOSMemHandle, pui8LinAddr);
                sDevPAddr = SysCpuPAddrToDevPAddr(psMMUAttrib->sDevId.eDeviceType, sCpuPAddr);
 
-               
+               /* how many bytes to dump from this page */
                if (ui32PageOffset + ui32Bytes > psMMUAttrib->ui32PTSize)
                {
-                       
+                       /* dump up to the page boundary */
                        ui32BlockBytes = psMMUAttrib->ui32PTSize - ui32PageOffset;
                }
                else
                {
-                       
+                       /* dump what's left */
                        ui32BlockBytes = ui32Bytes;
                }
 
-               
-
+               /*
+                       Write a comment to the MMU script stream indicating the page table load
+               */
                
                if (bInitialisePages)
                {
@@ -1086,11 +1313,11 @@ PVRSRV_ERROR PDumpMemPTEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
                {
                        for (ui32Offset = 0; ui32Offset < ui32BlockBytes; ui32Offset += sizeof(IMG_UINT32))
                        {
-                               IMG_UINT32 ui32PTE = *((IMG_UINT32 *)(IMG_UINTPTR_T)(pui8LinAddr + ui32Offset));  
+                               IMG_UINT32 ui32PTE = *((IMG_UINT32 *)(IMG_UINTPTR_T)(pui8LinAddr + ui32Offset)); /* PRQA S 3305 */ /* strict pointer */
 
                                if ((ui32PTE & psMMUAttrib->ui32PDEMask) != 0)
                                {
-                                       
+                                       /* PT entry points to non-null page */
 #if defined(SGX_FEATURE_36BIT_MMU)
                                        eErr = PDumpOSBufprintf(hScript,
                                                        ui32MaxLenScript,
@@ -1176,15 +1403,15 @@ PVRSRV_ERROR PDumpMemPTEntriesKM(PDUMP_MMU_ATTRIB *psMMUAttrib,
                        }
                }
 
-               
+               /* update details for next page */
 
-               
+               /* page offset 0 after first page dump */
                ui32PageOffset = 0;
-               
+               /* bytes left over */
                ui32Bytes -= ui32BlockBytes;
-               
+               /* advance the cpuVaddr */
                pui8LinAddr += ui32BlockBytes;
-               
+               /* update the file write offset */
                ui32ParamOutPos += ui32BlockBytes;
        }
 
@@ -1205,7 +1432,7 @@ PVRSRV_ERROR PDumpPDDevPAddrKM(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
        IMG_UINT32 ui32Flags = PDUMP_FLAGS_CONTINUOUS;
        IMG_UINT32 ui32ParamOutPos;
        PDUMP_MMU_ATTRIB *psMMUAttrib;
-       IMG_UINT32 ui32PageMask; 
+       IMG_UINT32 ui32PageMask; /* mask for the physical page backing the PT */
 
        PDUMP_GET_SCRIPT_AND_FILE_STRING();
 
@@ -1219,7 +1446,7 @@ PVRSRV_ERROR PDumpPDDevPAddrKM(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
 
        ui32ParamOutPos = PDumpOSGetStreamOffset(PDUMP_STREAM_PARAM2);
 
-       
+       /* Write the PD phys addr to the param stream up front */
        if(!PDumpOSWriteString(PDumpOSGetStream(PDUMP_STREAM_PARAM2),
                                                (IMG_UINT8 *)&sPDDevPAddr,
                                                sizeof(IMG_DEV_PHYADDR),
@@ -1241,7 +1468,9 @@ PVRSRV_ERROR PDumpPDDevPAddrKM(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
                return eErr;
        }
 
-       
+       /* Write a comment indicating the PD phys addr write, so that the offsets
+        * into the param stream increase in correspondence with the number of bytes
+        * written. */
        eErr = PDumpOSBufprintf(hScript,
                        ui32MaxLenScript,
                        "-- LDB :%s:PA_0x%08X%08X:0x%08X 0x%08X 0x%08X %s\r\n",
@@ -1258,7 +1487,6 @@ PVRSRV_ERROR PDumpPDDevPAddrKM(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
        }
        PDumpOSWriteString2(hScript, ui32Flags);
 
-       
        sDevVAddr = psMemInfo->sDevVAddr;
        ui32PageByteOffset = sDevVAddr.uiAddr & ui32PageMask;
 
@@ -1368,13 +1596,17 @@ PVRSRV_ERROR PDumpPDDevPAddrKM(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
        return PVRSRV_OK;
 }
 
-
-
-
+/**************************************************************************
+ * Function Name  : PDumpCommentKM
+ * Inputs         : pszComment, ui32Flags
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Dumps a comment
+**************************************************************************/
 PVRSRV_ERROR PDumpCommentKM(IMG_CHAR *pszComment, IMG_UINT32 ui32Flags)
 {
        PVRSRV_ERROR eErr;
-       IMG_CHAR pszCommentPrefix[] = "-- "; 
+       IMG_CHAR pszCommentPrefix[] = "-- "; /* prefix for comments */
 #if defined(PDUMP_DEBUG_OUTFILES)
        IMG_CHAR pszTemp[256];
 #endif
@@ -1382,17 +1614,19 @@ PVRSRV_ERROR PDumpCommentKM(IMG_CHAR *pszComment, IMG_UINT32 ui32Flags)
        PDUMP_GET_SCRIPT_STRING();
        PDUMP_DBG(("PDumpCommentKM"));
 #if defined(PDUMP_DEBUG_OUTFILES)
-       
+       /* include comments in the "extended" init phase.
+        * default is to ignore them.
+        */
        ui32Flags |= ( _PDumpIsPersistent() ) ? PDUMP_FLAGS_PERSISTENT : 0;
 #endif
-       
+       /* Put \r \n sequence at the end if it isn't already there */
        PDumpOSVerifyLineEnding(pszComment, ui32MaxLen);
 
-       
+       /* Length of string excluding terminating NULL character */
        ui32LenCommentPrefix = PDumpOSBuflen(pszCommentPrefix, sizeof(pszCommentPrefix));
 
-       
-       
+       /* Ensure output file is available for writing */
+       /* FIXME: is this necessary? */
        if (!PDumpOSWriteString(PDumpOSGetStream(PDUMP_STREAM_SCRIPT2),
                          (IMG_UINT8*)pszCommentPrefix,
                          ui32LenCommentPrefix,
@@ -1425,13 +1659,13 @@ PVRSRV_ERROR PDumpCommentKM(IMG_CHAR *pszComment, IMG_UINT32 ui32Flags)
        }
 
 #if defined(PDUMP_DEBUG_OUTFILES)
-       
+       /* Prefix comment with PID and line number */
        eErr = PDumpOSSprintf(pszTemp, 256, "%d-%d %s",
                _PDumpGetPID(),
                g_ui32EveryLineCounter,
                pszComment);
 
-       
+       /* Append the comment to the script stream */
        eErr = PDumpOSBufprintf(hScript, ui32MaxLen, "%s",
                pszTemp);
 #else
@@ -1447,14 +1681,22 @@ PVRSRV_ERROR PDumpCommentKM(IMG_CHAR *pszComment, IMG_UINT32 ui32Flags)
        return PVRSRV_OK;
 }
 
-
+/**************************************************************************
+ * Function Name  : PDumpCommentWithFlags
+ * Inputs         : psPDev - PDev for PDump device
+ *                               : pszFormat - format string for comment
+ *                               : ... - args for format string
+ * Outputs        : None
+ * Returns        : None
+ * Description    : PDumps a comments
+**************************************************************************/
 PVRSRV_ERROR PDumpCommentWithFlags(IMG_UINT32 ui32Flags, IMG_CHAR * pszFormat, ...)
 {
        PVRSRV_ERROR eErr;
        PDUMP_va_list ap;
        PDUMP_GET_MSG_STRING();
 
-       
+       /* Construct the string */
        PDUMP_va_start(ap, pszFormat);
        eErr = PDumpOSVSprintf(pszMsg, ui32MaxLen, pszFormat, ap);
        PDUMP_va_end(ap);
@@ -1466,13 +1708,22 @@ PVRSRV_ERROR PDumpCommentWithFlags(IMG_UINT32 ui32Flags, IMG_CHAR * pszFormat, .
        return PDumpCommentKM(pszMsg, ui32Flags);
 }
 
+/**************************************************************************
+ * Function Name  : PDumpComment
+ * Inputs         : psPDev - PDev for PDump device
+ *                               : pszFormat - format string for comment
+ *                               : ... - args for format string
+ * Outputs        : None
+ * Returns        : None
+ * Description    : PDumps a comments
+**************************************************************************/
 PVRSRV_ERROR PDumpComment(IMG_CHAR *pszFormat, ...)
 {
        PVRSRV_ERROR eErr;
        PDUMP_va_list ap;
        PDUMP_GET_MSG_STRING();
 
-       
+       /* Construct the string */
        PDUMP_va_start(ap, pszFormat);
        eErr = PDumpOSVSprintf(pszMsg, ui32MaxLen, pszFormat, ap);
        PDUMP_va_end(ap);
@@ -1484,20 +1735,27 @@ PVRSRV_ERROR PDumpComment(IMG_CHAR *pszFormat, ...)
        return PDumpCommentKM(pszMsg, PDUMP_FLAGS_CONTINUOUS);
 }
 
+/**************************************************************************
+ * Function Name  : PDumpDriverInfoKM
+ * Inputs         : pszString, ui32Flags
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Dumps a comment
+**************************************************************************/
 PVRSRV_ERROR PDumpDriverInfoKM(IMG_CHAR *pszString, IMG_UINT32 ui32Flags)
 {
        PVRSRV_ERROR eErr;
        IMG_UINT32      ui32MsgLen;
        PDUMP_GET_MSG_STRING();
 
-       
+       /* Construct the string */
        eErr = PDumpOSSprintf(pszMsg, ui32MaxLen, "%s", pszString);
        if(eErr != PVRSRV_OK)
        {
                return eErr;
        }
 
-       
+       /* Put \r \n sequence at the end if it isn't already there */
        PDumpOSVerifyLineEnding(pszMsg, ui32MaxLen);
        ui32MsgLen = PDumpOSBuflen(pszMsg, ui32MaxLen);
 
@@ -1518,6 +1776,30 @@ PVRSRV_ERROR PDumpDriverInfoKM(IMG_CHAR *pszString, IMG_UINT32 ui32Flags)
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PDumpBitmapKM
+
+ @Description
+
+ Dumps a bitmap from device memory to a file
+
+ @Input    psDevId
+ @Input    pszFileName
+ @Input    ui32FileOffset
+ @Input    ui32Width
+ @Input    ui32Height
+ @Input    ui32StrideInBytes
+ @Input    sDevBaseAddr
+ @Input    ui32Size
+ @Input    ePixelFormat
+ @Input    eMemFormat
+ @Input    ui32PDumpFlags
+
+ @Return   PVRSRV_ERROR                        :
+
+******************************************************************************/
 PVRSRV_ERROR PDumpBitmapKM(    PVRSRV_DEVICE_NODE *psDeviceNode,
                                                        IMG_CHAR *pszFileName,
                                                        IMG_UINT32 ui32FileOffset,
@@ -1543,7 +1825,7 @@ PVRSRV_ERROR PDumpBitmapKM(       PVRSRV_DEVICE_NODE *psDeviceNode,
 
        PDumpCommentWithFlags(ui32PDumpFlags, "\r\n-- Dump bitmap of render\r\n");
 
-       
+       /* find MMU context ID */
        ui32MMUContextID = psDeviceNode->pfnMMUGetContextID( hDevMemContext );
 
        eErr = PDumpOSBufprintf(hScript,
@@ -1570,6 +1852,25 @@ PVRSRV_ERROR PDumpBitmapKM(      PVRSRV_DEVICE_NODE *psDeviceNode,
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PDumpReadRegKM
+
+ @Description
+
+ Dumps a read from a device register to a file
+
+ @Input    psConnection                : connection info
+ @Input    pszFileName
+ @Input    ui32FileOffset
+ @Input    ui32Address
+ @Input    ui32Size
+ @Input    ui32PDumpFlags
+
+ @Return   PVRSRV_ERROR                        :
+
+******************************************************************************/
 PVRSRV_ERROR PDumpReadRegKM            (       IMG_CHAR *pszPDumpRegName,
                                                                        IMG_CHAR *pszFileName,
                                                                        IMG_UINT32 ui32FileOffset,
@@ -1599,12 +1900,19 @@ PVRSRV_ERROR PDumpReadRegKM             (       IMG_CHAR *pszPDumpRegName,
        return PVRSRV_OK;
 }
 
+/*****************************************************************************
+ @name         PDumpTestNextFrame
+ @brief                Tests whether the next frame will be pdumped
+ @param                ui32CurrentFrame
+ @return       bFrameDumped
+*****************************************************************************/
 IMG_BOOL PDumpTestNextFrame(IMG_UINT32 ui32CurrentFrame)
 {
        IMG_BOOL        bFrameDumped;
 
-       
-
+       /*
+               Try dumping a string
+       */
        (IMG_VOID) PDumpSetFrameKM(ui32CurrentFrame + 1);
        bFrameDumped = PDumpIsCaptureFrameKM();
        (IMG_VOID) PDumpSetFrameKM(ui32CurrentFrame);
@@ -1612,6 +1920,16 @@ IMG_BOOL PDumpTestNextFrame(IMG_UINT32 ui32CurrentFrame)
        return bFrameDumped;
 }
 
+/*****************************************************************************
+ @name         PDumpSignatureRegister
+ @brief                Dumps a single signature register
+ @param        psDevId - device ID
+ @param        ui32Address     - The register address
+ @param                ui32Size - The amount of data to be dumped in bytes
+ @param                pui32FileOffset - Offset of dump in output file
+ @param                ui32Flags - Flags
+ @return       none
+*****************************************************************************/
 static PVRSRV_ERROR PDumpSignatureRegister     (PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                                         IMG_CHAR       *pszFileName,
                                                                         IMG_UINT32             ui32Address,
@@ -1639,6 +1957,18 @@ static PVRSRV_ERROR PDumpSignatureRegister       (PVRSRV_DEVICE_IDENTIFIER *psDevId,
        return PVRSRV_OK;
 }
 
+/*****************************************************************************
+ @name         PDumpRegisterRange
+ @brief                Dumps a list of signature registers to a file
+ @param                psDevId - device ID
+ @param                pszFileName - target filename for dump
+ @param                pui32Registers - register list
+ @param                ui32NumRegisters - number of regs to dump
+ @param                pui32FileOffset - file offset
+ @param                ui32Size - size of write in bytes
+ @param                ui32Flags - pdump flags
+ @return       none
+ *****************************************************************************/
 static IMG_VOID PDumpRegisterRange(PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                                        IMG_CHAR *pszFileName,
                                                                        IMG_UINT32 *pui32Registers,
@@ -1654,6 +1984,14 @@ static IMG_VOID PDumpRegisterRange(PVRSRV_DEVICE_IDENTIFIER *psDevId,
        }
 }
 
+/*****************************************************************************
+ @name         PDump3DSignatureRegisters
+ @brief                Dumps the signature registers for 3D modules...
+ @param                psDevId - device ID info
+ @param                pui32Registers - register list
+ @param                ui32NumRegisters - number of regs to dump
+ @return       Error
+*****************************************************************************/
 PVRSRV_ERROR PDump3DSignatureRegisters(PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                                                IMG_UINT32 ui32DumpFrameNum,
                                                                                IMG_BOOL bLastFrame,
@@ -1686,6 +2024,17 @@ PVRSRV_ERROR PDump3DSignatureRegisters(PVRSRV_DEVICE_IDENTIFIER *psDevId,
        return PVRSRV_OK;
 }
 
+/*****************************************************************************
+ @name         PDumpTASignatureRegisters
+ @brief                Dumps the TA signature registers
+ @param                psDevId - device id info
+ @param                ui32DumpFrameNum - frame number
+ @param                ui32TAKickCount - TA kick counter
+ @param                bLastFrame
+ @param                pui32Registers - register list
+ @param                ui32NumRegisters - number of regs to dump
+ @return       Error
+*****************************************************************************/
 PVRSRV_ERROR PDumpTASignatureRegisters (PVRSRV_DEVICE_IDENTIFIER *psDevId,
                         IMG_UINT32 ui32DumpFrameNum,
                         IMG_UINT32     ui32TAKickCount,
@@ -1718,6 +2067,16 @@ PVRSRV_ERROR PDumpTASignatureRegisters   (PVRSRV_DEVICE_IDENTIFIER *psDevId,
        return PVRSRV_OK;
 }
 
+/*****************************************************************************
+ @name         PDumpCounterRegisters
+ @brief                Dumps the performance counters
+ @param                psDevId - device id info
+ @param                ui32DumpFrameNum - frame number
+ @param                bLastFrame
+ @param                pui32Registers - register list
+ @param                ui32NumRegisters - number of regs to dump
+ @return       Error
+*****************************************************************************/
 PVRSRV_ERROR PDumpCounterRegisters (PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                                IMG_UINT32 ui32DumpFrameNum,
                                                                IMG_BOOL        bLastFrame,
@@ -1750,6 +2109,14 @@ PVRSRV_ERROR PDumpCounterRegisters (PVRSRV_DEVICE_IDENTIFIER *psDevId,
        return PVRSRV_OK;
 }
 
+/*****************************************************************************
+ @name         PDumpRegRead
+ @brief                Dump signature register read to script
+ @param                pszPDumpDevName - pdump device name
+ @param                ui32RegOffset - register offset
+ @param                ui32Flags - pdump flags
+ @return       Error
+*****************************************************************************/
 PVRSRV_ERROR PDumpRegRead(IMG_CHAR *pszPDumpRegName,
                                                        const IMG_UINT32 ui32RegOffset,
                                                        IMG_UINT32 ui32Flags)
@@ -1768,6 +2135,17 @@ PVRSRV_ERROR PDumpRegRead(IMG_CHAR *pszPDumpRegName,
        return PVRSRV_OK;
 }
 
+/*****************************************************************************
+ @name         PDumpSaveMemKM
+ @brief                Save device memory to a file
+ @param                psDevId
+ @param                pszFileName
+ @param                ui32FileOffset
+ @param                sDevBaseAddr
+ @param                ui32Size
+ @param                ui32PDumpFlags
+ @return       Error
+*****************************************************************************/
 PVRSRV_ERROR PDumpSaveMemKM (PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                         IMG_CHAR                       *pszFileName,
                                                         IMG_UINT32                     ui32FileOffset,
@@ -1797,6 +2175,13 @@ PVRSRV_ERROR PDumpSaveMemKM (PVRSRV_DEVICE_IDENTIFIER *psDevId,
        return PVRSRV_OK;
 }
 
+/*****************************************************************************
+ @name         PDumpCycleCountRegRead
+ @brief                Dump counter register read to script
+ @param                ui32RegOffset - register offset
+ @param                bLastFrame
+ @return       Error
+*****************************************************************************/
 PVRSRV_ERROR PDumpCycleCountRegRead(PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                                        const IMG_UINT32 ui32RegOffset,
                                                                        IMG_BOOL bLastFrame)
@@ -1816,6 +2201,18 @@ PVRSRV_ERROR PDumpCycleCountRegRead(PVRSRV_DEVICE_IDENTIFIER *psDevId,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PDumpSignatureBuffer
+
+ @Description
+
+ Dumps a signature registers buffer
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR PDumpSignatureBuffer (PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                                   IMG_CHAR                     *pszFileName,
                                                                   IMG_CHAR                     *pszBufferType,
@@ -1838,6 +2235,18 @@ PVRSRV_ERROR PDumpSignatureBuffer (PVRSRV_DEVICE_IDENTIFIER *psDevId,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PDumpHWPerfCBKM
+
+ @Description
+
+ Dumps the HW Perf Circular Buffer
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR PDumpHWPerfCBKM (PVRSRV_DEVICE_IDENTIFIER *psDevId,
                                                          IMG_CHAR                      *pszFileName,
                                                          IMG_UINT32            ui32FileOffset,
@@ -1852,6 +2261,15 @@ PVRSRV_ERROR PDumpHWPerfCBKM (PVRSRV_DEVICE_IDENTIFIER *psDevId,
 }
 
 
+/*****************************************************************************
+ FUNCTION      : PDumpCBP
+
+ PURPOSE       : Dump CBP command to script
+
+ PARAMETERS    :
+
+ RETURNS       : None
+*****************************************************************************/
 PVRSRV_ERROR PDumpCBP(PPVRSRV_KERNEL_MEM_INFO          psROffMemInfo,
                          IMG_UINT32                                    ui32ROffOffset,
                          IMG_UINT32                                    ui32WPosVal,
@@ -1866,41 +2284,42 @@ PVRSRV_ERROR PDumpCBP(PPVRSRV_KERNEL_MEM_INFO           psROffMemInfo,
        IMG_DEV_VIRTADDR        sDevVAddr;
        IMG_DEV_PHYADDR         sDevPAddr;
        IMG_DEV_VIRTADDR        sDevVPageAddr;
-    
+    //IMG_CPU_PHYADDR     CpuPAddr;
        PDUMP_MMU_ATTRIB *psMMUAttrib;
 
        PDUMP_GET_SCRIPT_STRING();
 
        psMMUAttrib = ((BM_BUF*)psROffMemInfo->sMemBlk.hBuffer)->pMapping->pBMHeap->psMMUAttrib;
 
-       
+       /* Check the offset and size don't exceed the bounds of the allocation */
        PVR_ASSERT((ui32ROffOffset + sizeof(IMG_UINT32)) <= psROffMemInfo->uAllocSize);
 
        pui8LinAddr = psROffMemInfo->pvLinAddrKM;
        sDevVAddr = psROffMemInfo->sDevVAddr;
 
-       
+       /* Advance addresses by offset */
        pui8LinAddr += ui32ROffOffset;
        sDevVAddr.uiAddr += ui32ROffOffset;
 
-       
-
-
+       /*
+               query the buffer manager for the physical pages that back the
+               virtual address
+       */
        PDumpOSCPUVAddrToPhysPages(psROffMemInfo->sMemBlk.hOSMemHandle,
                        ui32ROffOffset,
                        pui8LinAddr,
                        psMMUAttrib->ui32DataPageMask,
                        &ui32PageOffset);
 
-       
+       /* calculate the DevV page address */
        sDevVPageAddr.uiAddr = sDevVAddr.uiAddr - ui32PageOffset;
 
        PVR_ASSERT((sDevVPageAddr.uiAddr & 0xFFF) == 0);
 
-       
+       /* get the physical page address based on the device virtual address */
        BM_GetPhysPageAddr(psROffMemInfo, sDevVPageAddr, &sDevPAddr);
 
-       
+       /* convert DevP page address to byte address */
        sDevPAddr.uiAddr += ui32PageOffset;
 
        eErr = PDumpOSBufprintf(hScript,
@@ -1922,6 +2341,13 @@ PVRSRV_ERROR PDumpCBP(PPVRSRV_KERNEL_MEM_INFO            psROffMemInfo,
 }
 
 
+/**************************************************************************
+ * Function Name  : PDumpIDLWithFlags
+ * Inputs         : Idle time in clocks
+ * Outputs        : None
+ * Returns        : Error
+ * Description    : Dump IDL command to script
+**************************************************************************/
 PVRSRV_ERROR PDumpIDLWithFlags(IMG_UINT32 ui32Clocks, IMG_UINT32 ui32Flags)
 {
        PVRSRV_ERROR eErr;
@@ -1938,11 +2364,31 @@ PVRSRV_ERROR PDumpIDLWithFlags(IMG_UINT32 ui32Clocks, IMG_UINT32 ui32Flags)
 }
 
 
+/**************************************************************************
+ * Function Name  : PDumpIDL
+ * Inputs         : Idle time in clocks
+ * Outputs        : None
+ * Returns        : Error
+ * Description    : Dump IDL command to script
+**************************************************************************/
 PVRSRV_ERROR PDumpIDL(IMG_UINT32 ui32Clocks)
 {
        return PDumpIDLWithFlags(ui32Clocks, PDUMP_FLAGS_CONTINUOUS);
 }
 
+/**************************************************************************
+ * Function Name  : PDumpMemUM
+ * Inputs         : pvAltLinAddrUM
+ *                               : pvLinAddrUM
+ *                               : psMemInfo
+ *                               : ui32Offset
+ *                               : ui32Bytes
+ *                               : ui32Flags
+ *                               : hUniqueTag
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Dump user mode memory
+**************************************************************************/
 PVRSRV_ERROR PDumpMemUM(PVRSRV_PER_PROCESS_DATA *psPerProc,
                                                IMG_PVOID pvAltLinAddrUM,
                                                IMG_PVOID pvLinAddrUM,
@@ -1954,12 +2400,14 @@ PVRSRV_ERROR PDumpMemUM(PVRSRV_PER_PROCESS_DATA *psPerProc,
 {
        IMG_VOID *pvAddrUM;
        IMG_VOID *pvAddrKM;
-       IMG_UINT32 ui32BytesDumped;
-       IMG_UINT32 ui32CurrentOffset;
+       PVRSRV_ERROR eError;
 
        if (psMemInfo->pvLinAddrKM != IMG_NULL && pvAltLinAddrUM == IMG_NULL)
        {
-               
+               /*
+                * There is a kernel virtual address for the memory that is
+                * being dumped, and no alternate user mode linear address.
+                */
                return PDumpMemKM(IMG_NULL,
                                           psMemInfo,
                                           ui32Offset,
@@ -1972,7 +2420,10 @@ PVRSRV_ERROR PDumpMemUM(PVRSRV_PER_PROCESS_DATA *psPerProc,
 
        pvAddrKM = GetTempBuffer();
 
-       
+       /*
+        * The memory to be dumped needs to be copied in from
+        * the client.  Dump the memory, a buffer at a time.
+        */
        PVR_ASSERT(pvAddrUM != IMG_NULL && pvAddrKM != IMG_NULL);
        if (pvAddrUM == IMG_NULL || pvAddrKM == IMG_NULL)
        {
@@ -1985,59 +2436,131 @@ PVRSRV_ERROR PDumpMemUM(PVRSRV_PER_PROCESS_DATA *psPerProc,
                PDumpCommentWithFlags(ui32Flags, "Dumping 0x%08x bytes of memory, in blocks of 0x%08x bytes", ui32Bytes, (IMG_UINT32)PDUMP_TEMP_BUFFER_SIZE);
        }
 
-       ui32CurrentOffset = ui32Offset;
-       for (ui32BytesDumped = 0; ui32BytesDumped < ui32Bytes;)
+       if (psMemInfo->ui32Flags & PVRSRV_MEM_SPARSE)
        {
-               PVRSRV_ERROR eError;
-               IMG_UINT32 ui32BytesToDump = MIN(PDUMP_TEMP_BUFFER_SIZE, ui32Bytes - ui32BytesDumped);
+               /*
+                       In case of sparse mappings we can't just copy the full range as not
+                       all pages are valid, instead we walk a page at a time only dumping
+                       if the a page exists at that address
+               */
+               IMG_UINT32 ui32BytesRemain = ui32Bytes;
+               IMG_UINT32 ui32InPageStart = ui32Offset & (~HOST_PAGEMASK);
+               IMG_UINT32 ui32PageOffset = ui32Offset & (HOST_PAGEMASK);
+               IMG_UINT32 ui32BytesToCopy = MIN(HOST_PAGESIZE() - ui32InPageStart, ui32BytesRemain);
 
-               eError = OSCopyFromUser(psPerProc,
-                                          pvAddrKM,
-                                          pvAddrUM,
-                                          ui32BytesToDump);
-               if (eError != PVRSRV_OK)
+               do
                {
-                       PVR_DPF((PVR_DBG_ERROR, "PDumpMemUM: OSCopyFromUser failed (%d)", eError));
-                       return eError;
-               }
+                       if (BM_MapPageAtOffset(BM_MappingHandleFromBuffer(psMemInfo->sMemBlk.hBuffer), ui32PageOffset))
+                       {
+                               eError = OSCopyFromUser(psPerProc,
+                                                          pvAddrKM,
+                                                          pvAddrUM,
+                                                          ui32BytesToCopy);
+                               if (eError != PVRSRV_OK)
+                               {
+                                       PVR_DPF((PVR_DBG_ERROR, "PDumpMemUM: OSCopyFromUser failed (%d)", eError));
+                                       return eError;
+                               }
 
-               eError = PDumpMemKM(pvAddrKM,
-                                          psMemInfo,
-                                          ui32CurrentOffset,
-                                          ui32BytesToDump,
-                                          ui32Flags,
-                                          hUniqueTag);
+                               /*
+                                       At this point we know we're dumping a valid page so call
+                                       the internal function
+                               */
+                               eError = _PDumpMemIntKM(pvAddrKM,
+                                                                               psMemInfo,
+                                                                               ui32PageOffset + ui32InPageStart,
+                                                                               ui32BytesToCopy,
+                                                                               ui32Flags,
+                                                                               hUniqueTag);
+               
+                               if (eError != PVRSRV_OK)
+                               {
+                                       /*
+                                        * If writing fails part way through, then some
+                                        * investigation is needed.
+                                        */
+                                       if (ui32BytesToCopy != 0)
+                                       {
+                                               PVR_DPF((PVR_DBG_ERROR, "PDumpMemUM: PDumpMemKM failed (%d)", eError));
+                                       }
+                                       PVR_ASSERT(ui32BytesToCopy == 0);
+                                       return eError;
+                               }
+                       }
 
-               if (eError != PVRSRV_OK)
+                       VPTR_INC(pvAddrUM, ui32BytesToCopy);
+                       ui32BytesRemain -= ui32BytesToCopy;
+                       ui32InPageStart = 0;
+                       ui32PageOffset += HOST_PAGESIZE();
+               } while(ui32BytesRemain);
+       }
+       else
+       {
+               IMG_UINT32 ui32CurrentOffset = ui32Offset;
+               IMG_UINT32 ui32BytesDumped;
+
+               for (ui32BytesDumped = 0; ui32BytesDumped < ui32Bytes;)
                {
-                       
-                       if (ui32BytesDumped != 0)
+                       IMG_UINT32 ui32BytesToDump = MIN(PDUMP_TEMP_BUFFER_SIZE, ui32Bytes - ui32BytesDumped);
+       
+                       eError = OSCopyFromUser(psPerProc,
+                                                  pvAddrKM,
+                                                  pvAddrUM,
+                                                  ui32BytesToDump);
+                       if (eError != PVRSRV_OK)
                        {
-                               PVR_DPF((PVR_DBG_ERROR, "PDumpMemUM: PDumpMemKM failed (%d)", eError));
+                               PVR_DPF((PVR_DBG_ERROR, "PDumpMemUM: OSCopyFromUser failed (%d)", eError));
+                               return eError;
                        }
-                       PVR_ASSERT(ui32BytesDumped == 0);
-                       return eError;
+       
+                       eError = PDumpMemKM(pvAddrKM,
+                                                  psMemInfo,
+                                                  ui32CurrentOffset,
+                                                  ui32BytesToDump,
+                                                  ui32Flags,
+                                                  hUniqueTag);
+       
+                       if (eError != PVRSRV_OK)
+                       {
+                               /*
+                                * If writing fails part way through, then some
+                                * investigation is needed.
+                                */
+                               if (ui32BytesDumped != 0)
+                               {
+                                       PVR_DPF((PVR_DBG_ERROR, "PDumpMemUM: PDumpMemKM failed (%d)", eError));
+                               }
+                               PVR_ASSERT(ui32BytesDumped == 0);
+                               return eError;
+                       }
+       
+                       VPTR_INC(pvAddrUM, ui32BytesToDump);
+                       ui32CurrentOffset += ui32BytesToDump;
+                       ui32BytesDumped += ui32BytesToDump;
                }
-
-               VPTR_INC(pvAddrUM, ui32BytesToDump);
-               ui32CurrentOffset += ui32BytesToDump;
-               ui32BytesDumped += ui32BytesToDump;
        }
 
        return PVRSRV_OK;
 }
 
 
+/**************************************************************************
+ * Function Name  : _PdumpAllocMMUContext
+ * Inputs         : pui32MMUContextID
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : pdump util to allocate MMU contexts
+**************************************************************************/
 static PVRSRV_ERROR _PdumpAllocMMUContext(IMG_UINT32 *pui32MMUContextID)
 {
        IMG_UINT32 i;
 
-       
+       /* there are MAX_PDUMP_MMU_CONTEXTS contexts available, find one */
        for(i=0; i<MAX_PDUMP_MMU_CONTEXTS; i++)
        {
                if((gui16MMUContextUsage & (1U << i)) == 0)
                {
-                       
+                       /* mark in use */
                        gui16MMUContextUsage |= 1U << i;
                        *pui32MMUContextID = i;
                        return PVRSRV_OK;
@@ -2050,11 +2573,18 @@ static PVRSRV_ERROR _PdumpAllocMMUContext(IMG_UINT32 *pui32MMUContextID)
 }
 
 
+/**************************************************************************
+ * Function Name  : _PdumpFreeMMUContext
+ * Inputs         : ui32MMUContextID
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : pdump util to free MMU contexts
+**************************************************************************/
 static PVRSRV_ERROR _PdumpFreeMMUContext(IMG_UINT32 ui32MMUContextID)
 {
        if(ui32MMUContextID < MAX_PDUMP_MMU_CONTEXTS)
        {
-               
+               /* free the id */
                gui16MMUContextUsage &= ~(1U << ui32MMUContextID);
                return PVRSRV_OK;
        }
@@ -2065,6 +2595,13 @@ static PVRSRV_ERROR _PdumpFreeMMUContext(IMG_UINT32 ui32MMUContextID)
 }
 
 
+/**************************************************************************
+ * Function Name  : PDumpSetMMUContext
+ * Inputs         :
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Set MMU Context
+**************************************************************************/
 PVRSRV_ERROR PDumpSetMMUContext(PVRSRV_DEVICE_TYPE eDeviceType,
                                                                IMG_CHAR *pszMemSpace,
                                                                IMG_UINT32 *pui32MMUContextID,
@@ -2087,11 +2624,11 @@ PVRSRV_ERROR PDumpSetMMUContext(PVRSRV_DEVICE_TYPE eDeviceType,
                return eErr;
        }
 
-       
-       
+       /* derive the DevPAddr */
+       /* FIXME: if we used OSMemHandleToCPUPAddr() here, we could lose the lin addr arg */
        sCpuPAddr = OSMapLinToCPUPhys(hOSMemHandle, pui8LinAddr);
        sDevPAddr = SysCpuPAddrToDevPAddr(eDeviceType, sCpuPAddr);
-       
+       /* and round to 4k page */
        sDevPAddr.uiAddr &= ~((PVRSRV_4K_PAGE_SIZE) -1);
 
        eErr = PDumpOSBufprintf(hScript,
@@ -2109,13 +2646,20 @@ PVRSRV_ERROR PDumpSetMMUContext(PVRSRV_DEVICE_TYPE eDeviceType,
        }
        PDumpOSWriteString2(hScript, PDUMP_FLAGS_CONTINUOUS);
 
-       
+       /* return the MMU Context ID */
        *pui32MMUContextID = ui32MMUContextID;
 
        return PVRSRV_OK;
 }
 
 
+/**************************************************************************
+ * Function Name  : PDumpClearMMUContext
+ * Inputs         :
+ * Outputs        : None
+ * Returns        : PVRSRV_ERROR
+ * Description    : Clear MMU Context
+**************************************************************************/
 PVRSRV_ERROR PDumpClearMMUContext(PVRSRV_DEVICE_TYPE eDeviceType,
                                                                IMG_CHAR *pszMemSpace,
                                                                IMG_UINT32 ui32MMUContextID,
@@ -2126,7 +2670,9 @@ PVRSRV_ERROR PDumpClearMMUContext(PVRSRV_DEVICE_TYPE eDeviceType,
        PVR_UNREFERENCED_PARAMETER(eDeviceType);
        PVR_UNREFERENCED_PARAMETER(ui32MMUType);
 
-       
+       /* FIXME: Propagate error from PDumpComment once it's supported on
+        * all OSes and platforms
+        */
        PDumpComment("Clear MMU Context for memory space %s\r\n", pszMemSpace);
        eErr = PDumpOSBufprintf(hScript,
                                                ui32MaxLen, 
@@ -2149,6 +2695,15 @@ PVRSRV_ERROR PDumpClearMMUContext(PVRSRV_DEVICE_TYPE eDeviceType,
        return PVRSRV_OK;
 }
 
+/*****************************************************************************
+ FUNCTION      : PDumpStoreMemToFile
+    
+ PURPOSE       : Dumps a given addr:size to a file
+
+ PARAMETERS    :
+
+ RETURNS       : 
+*****************************************************************************/
 PVRSRV_ERROR PDumpStoreMemToFile(PDUMP_MMU_ATTRIB *psMMUAttrib,
                                                         IMG_CHAR *pszFileName,
                                                                 IMG_UINT32 ui32FileOffset, 
@@ -2164,18 +2719,19 @@ PVRSRV_ERROR PDumpStoreMemToFile(PDUMP_MMU_ATTRIB *psMMUAttrib,
 
        PDUMP_GET_SCRIPT_STRING();
 
-       
-
-
+       /*
+               query the buffer manager for the physical pages that back the
+               virtual address
+       */
        ui32PageOffset = (IMG_UINT32)((IMG_UINTPTR_T)psMemInfo->pvLinAddrKM & psMMUAttrib->ui32DataPageMask);
        
-       
+       /* calculate the DevV page address */
        sDevVPageAddr.uiAddr = uiAddr - ui32PageOffset;
        
-       
+       /* get the physical page address based on the device virtual address */
        BM_GetPhysPageAddr(psMemInfo, sDevVPageAddr, &sDevPAddr);
        
-       
+       /* convert DevP page address to byte address */
        sDevPAddr.uiAddr += ui32PageOffset;
 
        PDumpOSBufprintf(hScript,
@@ -2194,6 +2750,15 @@ PVRSRV_ERROR PDumpStoreMemToFile(PDUMP_MMU_ATTRIB *psMMUAttrib,
        return PVRSRV_OK;       
 }
 
+/*****************************************************************************
+ FUNCTION      : PDumpRegBasedCBP
+    
+ PURPOSE       : Dump CBP command to script
+
+ PARAMETERS    :
+                         
+ RETURNS       : None
+*****************************************************************************/
 PVRSRV_ERROR PDumpRegBasedCBP(IMG_CHAR         *pszPDumpRegName,
                                                          IMG_UINT32    ui32RegOffset,
                                                          IMG_UINT32    ui32WPosVal,
@@ -2217,16 +2782,26 @@ PVRSRV_ERROR PDumpRegBasedCBP(IMG_CHAR          *pszPDumpRegName,
 }
 
 
+/****************************************************
+ * Non-uitron code here.
+ * For example, code communicating with dbg driver.
+ ***************************************************/
+/* PRQA S 5087 1 */ /* include file needed here */
 #include "syscommon.h"
 
+/**************************************************************************
+ * Function Name  : PDumpConnectionNotify
+ * Description    : Called by the debugdrv to tell Services that pdump has
+ *                                     connected
+ *                                     NOTE: No debugdrv on uitron.
+ **************************************************************************/
 IMG_EXPORT IMG_VOID PDumpConnectionNotify(IMG_VOID)
 {
        SYS_DATA                        *psSysData;
        PVRSRV_DEVICE_NODE      *psThis;
        PVR_DPF((PVR_DBG_WARNING, "PDump has connected."));
        
-       
+       /* Loop over all known devices */
        SysAcquireData(&psSysData);
        
        psThis = psSysData->psDeviceNodeList;
@@ -2234,27 +2809,39 @@ IMG_EXPORT IMG_VOID PDumpConnectionNotify(IMG_VOID)
        {
                if (psThis->pfnPDumpInitDevice)
                {
-                       
+                       /* Reset pdump according to connected device */
                        psThis->pfnPDumpInitDevice(psThis);
                }
                psThis = psThis->psNext;
        }
 }
 
+/*****************************************************************************
+ * Function Name  : DbgWrite
+ * Inputs         : psStream - debug stream to write to
+                                       pui8Data - buffer
+                                       ui32BCount - buffer length
+                                       ui32Flags - flags, e.g. continuous, LF
+ * Outputs        : None
+ * Returns        : Bytes written
+ * Description    : Write a block of data to a debug stream
+ *                                     NOTE: No debugdrv on uitron.
+ *****************************************************************************/
 IMG_UINT32 DbgWrite(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_UINT32 ui32BCount, IMG_UINT32 ui32Flags)
 {
        IMG_UINT32      ui32BytesWritten = 0;
        IMG_UINT32      ui32Off = 0;
        PDBG_STREAM_CONTROL psCtrl = psStream->psCtrl;
 
-       
+       /* Return immediately if marked as "never" */
        if ((ui32Flags & PDUMP_FLAGS_NEVER) != 0)
        {
                return ui32BCount;
        }
        
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-       
+       /* Return if process is not marked for pdumping, unless it's persistent.
+        */
        if ( (_PDumpIsProcessActive() == IMG_FALSE ) &&
                 ((ui32Flags & PDUMP_FLAGS_PERSISTENT) == 0) )
        {
@@ -2262,14 +2849,18 @@ IMG_UINT32 DbgWrite(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_UINT32 ui32BC
        }
 #endif
 
-       
+       /* Send persistent data first ...
+        * If we're still initialising the params will be captured to the
+        * init stream in the call to pfnDBGDrivWrite2 below.
+        */
        if ( ((ui32Flags & PDUMP_FLAGS_PERSISTENT) != 0) && (psCtrl->bInitPhaseComplete) )
        {
                while (ui32BCount > 0)
                {
-                       
-
-
+                       /*
+                               Params marked as persistent should be appended to the init phase.
+                               For example window system mem mapping of the primary surface.
+                       */
                        ui32BytesWritten = PDumpOSDebugDriverWrite(     psStream,
                                                                                                                PDUMP_WRITE_MODE_PERSISTENT,
                                                                                                                &pui8Data[ui32Off], ui32BCount, 1, 0);
@@ -2289,14 +2880,14 @@ IMG_UINT32 DbgWrite(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_UINT32 ui32BC
                                PVR_DPF((PVR_DBG_ERROR, "DbgWrite: Failed to send persistent data"));
                                if( (psCtrl->ui32Flags & DEBUG_FLAGS_READONLY) != 0)
                                {
-                                       
+                                       /* suspend pdump to prevent flooding kernel log buffer */
                                        PDumpSuspendKM();
                                }
                                return 0xFFFFFFFFU;
                        }
                }
                
-               
+               /* reset buffer counters */
                ui32BCount = ui32Off; ui32Off = 0; ui32BytesWritten = 0;
        }
 
@@ -2304,8 +2895,9 @@ IMG_UINT32 DbgWrite(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_UINT32 ui32BC
        {
                if ((ui32Flags & PDUMP_FLAGS_CONTINUOUS) != 0)
                {
-                       
-
+                       /*
+                               If pdump client (or its equivalent) isn't running then throw continuous data away.
+                       */
                        if (((psCtrl->ui32CapMode & DEBUG_CAPMODE_FRAMED) != 0) &&
                                 (psCtrl->ui32Start == 0xFFFFFFFFU) &&
                                 (psCtrl->ui32End == 0xFFFFFFFFU) &&
@@ -2344,9 +2936,10 @@ IMG_UINT32 DbgWrite(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_UINT32 ui32BC
                        }
                }
 
-               
-
-
+               /*
+                       If the debug driver's buffers are full so no data could be written then yield
+                       execution so pdump can run and empty them.
+               */
                if (ui32BytesWritten == 0)
                {
                        PDumpOSReleaseExecution();
@@ -2358,15 +2951,17 @@ IMG_UINT32 DbgWrite(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_UINT32 ui32BC
                        ui32BCount -= ui32BytesWritten;
                }
 
-               
+               /* loop exits when i) all data is written, or ii) an unrecoverable error occurs */
        }
 
-
-       
        return ui32BytesWritten;
 }
 
 
 
-#else  
-#endif 
+#else  /* defined(PDUMP) */
+/* disable warning about empty module */
+#endif /* defined(PDUMP) */
+/*****************************************************************************
+ End of file (pdump_common.c)
+*****************************************************************************/
index eb73166..3918bb2 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Per-process storage
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Manage per-process storage
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
 #include "resman.h"
 
 static HASH_TABLE *psHashTab = IMG_NULL;
 
+/*!
+******************************************************************************
+
+ @Function     FreePerProcData
+
+ @Description  Free a per-process data area
+
+ @Input                psPerProc - pointer to per-process data area
+
+ @Return       Error code, or PVRSRV_OK
+
+******************************************************************************/
 static PVRSRV_ERROR FreePerProcessData(PVRSRV_PER_PROCESS_DATA *psPerProc)
 {
        PVRSRV_ERROR eError;
@@ -54,7 +82,10 @@ static PVRSRV_ERROR FreePerProcessData(PVRSRV_PER_PROCESS_DATA *psPerProc)
        if (uiPerProc == 0)
        {
                PVR_DPF((PVR_DBG_ERROR, "FreePerProcessData: Couldn't find process in per-process data hash table"));
-               
+               /*
+                * We must have failed early in the per-process data area
+                * creation, before the process ID was set.
+                */
                PVR_ASSERT(psPerProc->ui32PID == 0);
        }
        else
@@ -63,7 +94,7 @@ static PVRSRV_ERROR FreePerProcessData(PVRSRV_PER_PROCESS_DATA *psPerProc)
                PVR_ASSERT(((PVRSRV_PER_PROCESS_DATA *)uiPerProc)->ui32PID == psPerProc->ui32PID);
        }
 
-       
+       /* Free handle base for this process */
        if (psPerProc->psHandleBase != IMG_NULL)
        {
                eError = PVRSRVFreeHandleBase(psPerProc->psHandleBase);
@@ -74,7 +105,7 @@ static PVRSRV_ERROR FreePerProcessData(PVRSRV_PER_PROCESS_DATA *psPerProc)
                }
        }
 
-       
+       /* Release handle for per-process data area */
        if (psPerProc->hPerProcData != IMG_NULL)
        {
                eError = PVRSRVReleaseHandle(KERNEL_HANDLE_BASE, psPerProc->hPerProcData, PVRSRV_HANDLE_TYPE_PERPROC_DATA);
@@ -86,7 +117,7 @@ static PVRSRV_ERROR FreePerProcessData(PVRSRV_PER_PROCESS_DATA *psPerProc)
                }
        }
 
-       
+       /* Call environment specific per process deinit function */
        eError = OSPerProcessPrivateDataDeInit(psPerProc->hOsPrivateData);
        if (eError != PVRSRV_OK)
        {
@@ -98,7 +129,7 @@ static PVRSRV_ERROR FreePerProcessData(PVRSRV_PER_PROCESS_DATA *psPerProc)
                sizeof(*psPerProc),
                psPerProc,
                psPerProc->hBlockAlloc);
-       
+       /*not nulling pointer, copy on stack*/
        if (eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR, "FreePerProcessData: Couldn't free per-process data (%d)", eError));
@@ -109,18 +140,44 @@ static PVRSRV_ERROR FreePerProcessData(PVRSRV_PER_PROCESS_DATA *psPerProc)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVPerProcessData
+ @Description  Return per-process data area
+
+ @Input                ui32PID - process ID
+ @Return       Pointer to per-process data area, or IMG_NULL on error.
+
+******************************************************************************/
 PVRSRV_PER_PROCESS_DATA *PVRSRVPerProcessData(IMG_UINT32 ui32PID)
 {
        PVRSRV_PER_PROCESS_DATA *psPerProc;
 
        PVR_ASSERT(psHashTab != IMG_NULL);
 
-       
+       /* Look for existing per-process data area */
        psPerProc = (PVRSRV_PER_PROCESS_DATA *)HASH_Retrieve(psHashTab, (IMG_UINTPTR_T)ui32PID);
        return psPerProc;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVPerProcessDataConnect
+ @Description  Allocate per-process data area, or increment refcount if one
+                               already exists for this PID.
+
+ @Input                ui32PID - process ID
+                       ppsPerProc - Pointer to per-process data area
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVPerProcessDataConnect(IMG_UINT32    ui32PID, IMG_UINT32 ui32Flags)
 {
        PVRSRV_PER_PROCESS_DATA *psPerProc;
@@ -132,12 +189,12 @@ PVRSRV_ERROR PVRSRVPerProcessDataConnect(IMG_UINT32       ui32PID, IMG_UINT32 ui32Flag
                return PVRSRV_ERROR_INIT_FAILURE;
        }
 
-       
+       /* Look for existing per-process data area */
        psPerProc = (PVRSRV_PER_PROCESS_DATA *)HASH_Retrieve(psHashTab, (IMG_UINTPTR_T)ui32PID);
 
        if (psPerProc == IMG_NULL)
        {
-               
+               /* Allocate per-process data area */
                eError = OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                                        sizeof(*psPerProc),
                                                        (IMG_PVOID *)&psPerProc,
@@ -170,7 +227,7 @@ PVRSRV_ERROR PVRSRVPerProcessDataConnect(IMG_UINT32 ui32PID, IMG_UINT32 ui32Flag
                PVR_UNREFERENCED_PARAMETER(ui32Flags);
 #endif
 
-               
+               /* Call environment specific per process init function */
                eError = OSPerProcessPrivateDataInit(&psPerProc->hOsPrivateData);
                if (eError != PVRSRV_OK)
                {
@@ -178,7 +235,7 @@ PVRSRV_ERROR PVRSRVPerProcessDataConnect(IMG_UINT32 ui32PID, IMG_UINT32 ui32Flag
                        goto failure;
                }
 
-               
+               /* Allocate a handle for the per-process data area */
                eError = PVRSRVAllocHandle(KERNEL_HANDLE_BASE,
                                                                   &psPerProc->hPerProcData,
                                                                   psPerProc,
@@ -190,7 +247,7 @@ PVRSRV_ERROR PVRSRVPerProcessDataConnect(IMG_UINT32 ui32PID, IMG_UINT32 ui32Flag
                        goto failure;
                }
 
-               
+               /* Allocate handle base for this process */
                eError = PVRSRVAllocHandleBase(&psPerProc->psHandleBase);
                if (eError != PVRSRV_OK)
                {
@@ -198,7 +255,7 @@ PVRSRV_ERROR PVRSRVPerProcessDataConnect(IMG_UINT32 ui32PID, IMG_UINT32 ui32Flag
                        goto failure;
                }
 
-               
+               /* Set per-process handle options */
                eError = OSPerProcessSetHandleOptions(psPerProc->psHandleBase);
                if (eError != PVRSRV_OK)
                {
@@ -206,7 +263,7 @@ PVRSRV_ERROR PVRSRVPerProcessDataConnect(IMG_UINT32 ui32PID, IMG_UINT32 ui32Flag
                        goto failure;
                }
                
-               
+               /* Create a resource manager context for the process */
                eError = PVRSRVResManConnect(psPerProc, &psPerProc->hResManContext);
                if (eError != PVRSRV_OK)
                {
@@ -231,6 +288,19 @@ failure:
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVPerProcessDataDisconnect
+ @Description  Decrement refcount for per-process data area, 
+                               and free the resources if necessary.
+
+ @Input                ui32PID - process ID
+ @Return       IMG_VOID
+
+******************************************************************************/
 IMG_VOID PVRSRVPerProcessDataDisconnect(IMG_UINT32     ui32PID)
 {
        PVRSRV_ERROR eError;
@@ -251,14 +321,14 @@ IMG_VOID PVRSRVPerProcessDataDisconnect(IMG_UINT32        ui32PID)
                        PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVPerProcessDataDisconnect: "
                                        "Last close from process 0x%x received", ui32PID));
 
+                       /* Close the Resource Manager connection */
+                       PVRSRVResManDisconnect(psPerProc->hResManContext, IMG_FALSE);
+
 #if defined (TTRACE)
                        PVRSRVTimeTraceBufferDestroy(ui32PID);
 #endif
 
-                       
-                       PVRSRVResManDisconnect(psPerProc->hResManContext, IMG_FALSE);
-                       
-                       
+                       /* Free the per-process data */
                        eError = FreePerProcessData(psPerProc);
                        if (eError != PVRSRV_OK)
                        {
@@ -275,11 +345,21 @@ IMG_VOID PVRSRVPerProcessDataDisconnect(IMG_UINT32        ui32PID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVPerProcessDataInit
+
+ @Description  Initialise per-process data management
+
+ @Return       Error code, or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVPerProcessDataInit(IMG_VOID)
 {
        PVR_ASSERT(psHashTab == IMG_NULL);
 
-       
+       /* Create hash table */
        psHashTab = HASH_Create(HASH_TAB_INIT_SIZE);
        if (psHashTab == IMG_NULL)
        {
@@ -290,12 +370,22 @@ PVRSRV_ERROR PVRSRVPerProcessDataInit(IMG_VOID)
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVPerProcessDataDeInit
+
+ @Description  De-initialise per-process data management
+
+ @Return       Error code, or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVPerProcessDataDeInit(IMG_VOID)
 {
-       
+       /* Destroy per-process data area hash table */
        if (psHashTab != IMG_NULL)
        {
-               
+               /* Free the hash table */
                HASH_Delete(psHashTab);
                psHashTab = IMG_NULL;
        }
@@ -303,3 +393,6 @@ PVRSRV_ERROR PVRSRVPerProcessDataDeInit(IMG_VOID)
        return PVRSRV_OK;
 }
 
+/******************************************************************************
+ End of file (perproc.c)
+******************************************************************************/
index 21d7ad4..511a690 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Power management functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Main APIs for power management functions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
 #include "pdump_km.h"
@@ -33,6 +49,19 @@ static IMG_BOOL gbInitServerRunning = IMG_FALSE;
 static IMG_BOOL gbInitServerRan = IMG_FALSE;
 static IMG_BOOL gbInitSuccessful = IMG_FALSE;
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSetInitServerState
+
+ @Description  Sets given services init state.
+
+ @Input                eInitServerState : a services init state
+ @Input                bState : a state to set
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVSetInitServerState(PVRSRV_INIT_SERVER_STATE eInitServerState, IMG_BOOL bState)
 {
@@ -57,6 +86,18 @@ PVRSRV_ERROR PVRSRVSetInitServerState(PVRSRV_INIT_SERVER_STATE eInitServerState,
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVGetInitServerState
+
+ @Description  Tests whether a given services init state was run.
+
+ @Input                eInitServerState : a services init state
+
+ @Return       IMG_BOOL
+
+******************************************************************************/
 IMG_EXPORT
 IMG_BOOL PVRSRVGetInitServerState(PVRSRV_INIT_SERVER_STATE eInitServerState)
 {
@@ -82,12 +123,38 @@ IMG_BOOL PVRSRVGetInitServerState(PVRSRV_INIT_SERVER_STATE eInitServerState)
        return bReturnVal;
 }
 
+/*!
+******************************************************************************
+
+ @Function     _IsSystemStatePowered
+
+ @Description  Tests whether a given system state represents powered-up.
+
+ @Input                eSystemPowerState : a system power state
+
+ @Return       IMG_BOOL
+
+******************************************************************************/
 static IMG_BOOL _IsSystemStatePowered(PVRSRV_SYS_POWER_STATE eSystemPowerState)
 {
        return (IMG_BOOL)(eSystemPowerState < PVRSRV_SYS_POWER_STATE_D2);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVPowerLock
+
+ @Description  Obtain the mutex for power transitions
+
+ @Input                ui32CallerID : KERNEL_ID or ISR_ID
+ @Input                bSystemPowerEvent : Only pass IMG_TRUE if the lock is for a
+                                                               system power state change
+
+ @Return       PVRSRV_ERROR IMG_CALLCONV
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVPowerLock(IMG_UINT32        ui32CallerID,
                                                         IMG_BOOL       bSystemPowerEvent)
@@ -115,8 +182,9 @@ PVRSRV_ERROR PVRSRVPowerLock(IMG_UINT32     ui32CallerID,
                }
                else if (bTryLock)
                {
-                       
-
+                       /*
+                               ISR failed to acquire lock so it must be held by a kernel thread.
+                       */
                        eError = PVRSRV_ERROR_RETRY;
                        break;
                }
@@ -130,12 +198,12 @@ PVRSRV_ERROR PVRSRVPowerLock(IMG_UINT32   ui32CallerID,
                OSPowerLockUnwrap();
        }
 
-        
+       /* PRQA S 3415 3 */ /* side effects desired */
        if ((eError == PVRSRV_OK) &&
                !bSystemPowerEvent &&
                !_IsSystemStatePowered(psSysData->eCurrentPowerState))
        {
-               
+               /* Reject device power state change due to system power state. */
                PVRSRVPowerUnlock(ui32CallerID);
                eError = PVRSRV_ERROR_RETRY;
        }
@@ -144,6 +212,18 @@ PVRSRV_ERROR PVRSRVPowerLock(IMG_UINT32    ui32CallerID,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVPowerUnlock
+
+ @Description  Release the mutex for power transitions
+
+ @Input                ui32CallerID : KERNEL_ID or ISR_ID
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 IMG_VOID PVRSRVPowerUnlock(IMG_UINT32  ui32CallerID)
 {
@@ -152,17 +232,36 @@ IMG_VOID PVRSRVPowerUnlock(IMG_UINT32     ui32CallerID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDevicePrePowerStateKM_AnyVaCb
+
+ @Description
+
+ Perform device-specific processing required before a power transition
+
+ @Input                psPowerDevice : the device
+ @Input                va : variable argument list with:
+                               bAllDevices : IMG_TRUE - All devices
+                                                         IMG_FALSE - Use ui32DeviceIndex
+                               ui32DeviceIndex : device index
+                               eNewPowerState : New power state
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR PVRSRVDevicePrePowerStateKM_AnyVaCb(PVRSRV_POWER_DEV *psPowerDevice, va_list va)
 {
        PVRSRV_DEV_POWER_STATE  eNewDevicePowerState;
        PVRSRV_ERROR                    eError;
 
-       
+       /*Variable Argument variables*/
        IMG_BOOL                                bAllDevices;
        IMG_UINT32                              ui32DeviceIndex;
        PVRSRV_DEV_POWER_STATE  eNewPowerState;
 
-       
+       /* WARNING: if types were not aligned to 4 bytes, this could be dangerous. */
        bAllDevices = va_arg(va, IMG_BOOL);
        ui32DeviceIndex = va_arg(va, IMG_UINT32);
        eNewPowerState = va_arg(va, PVRSRV_DEV_POWER_STATE);
@@ -176,7 +275,7 @@ static PVRSRV_ERROR PVRSRVDevicePrePowerStateKM_AnyVaCb(PVRSRV_POWER_DEV *psPowe
                {
                        if (psPowerDevice->pfnPrePower != IMG_NULL)
                        {
-                               
+                               /* Call the device's power callback. */
                                eError = psPowerDevice->pfnPrePower(psPowerDevice->hDevCookie,
                                                                                                        eNewDevicePowerState,
                                                                                                        psPowerDevice->eCurrentPowerState);
@@ -186,7 +285,7 @@ static PVRSRV_ERROR PVRSRVDevicePrePowerStateKM_AnyVaCb(PVRSRV_POWER_DEV *psPowe
                                }
                        }
 
-                       
+                       /* Do any required system-layer processing. */
                        eError = SysDevicePrePowerState(psPowerDevice->ui32DeviceIndex,
                                                                                        eNewDevicePowerState,
                                                                                        psPowerDevice->eCurrentPowerState);
@@ -200,6 +299,23 @@ static PVRSRV_ERROR PVRSRVDevicePrePowerStateKM_AnyVaCb(PVRSRV_POWER_DEV *psPowe
        return  PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDevicePrePowerStateKM
+
+ @Description
+
+ Perform device-specific processing required before a power transition
+
+ @Input                bAllDevices : IMG_TRUE - All devices
+                                                 IMG_FALSE - Use ui32DeviceIndex
+ @Input                ui32DeviceIndex : device index
+ @Input                eNewPowerState : New power state
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 static
 PVRSRV_ERROR PVRSRVDevicePrePowerStateKM(IMG_BOOL                              bAllDevices,
                                                                                 IMG_UINT32                             ui32DeviceIndex,
@@ -210,7 +326,7 @@ PVRSRV_ERROR PVRSRVDevicePrePowerStateKM(IMG_BOOL                           bAllDevices,
 
        SysAcquireData(&psSysData);
 
-       
+       /* Loop through the power devices. */
        eError = List_PVRSRV_POWER_DEV_PVRSRV_ERROR_Any_va(psSysData->psPowerDeviceList,
                                                                                                                &PVRSRVDevicePrePowerStateKM_AnyVaCb,
                                                                                                                bAllDevices,
@@ -220,17 +336,36 @@ PVRSRV_ERROR PVRSRVDevicePrePowerStateKM(IMG_BOOL                         bAllDevices,
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDevicePostPowerStateKM_AnyVaCb
+
+ @Description
+
+ Perform device-specific processing required after a power transition
+
+ @Input                psPowerDevice : the device
+ @Input                va : variable argument list with:
+                               bAllDevices : IMG_TRUE - All devices
+                                                         IMG_FALSE - Use ui32DeviceIndex
+                               ui32DeviceIndex : device index
+                               eNewPowerState : New power state
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR PVRSRVDevicePostPowerStateKM_AnyVaCb(PVRSRV_POWER_DEV *psPowerDevice, va_list va)
 {
        PVRSRV_DEV_POWER_STATE  eNewDevicePowerState;
        PVRSRV_ERROR                    eError;
 
-       
+       /*Variable Argument variables*/
        IMG_BOOL                                bAllDevices;
        IMG_UINT32                              ui32DeviceIndex;
        PVRSRV_DEV_POWER_STATE  eNewPowerState;
 
-       
+       /* WARNING: if types were not aligned to 4 bytes, this could be dangerous. */
        bAllDevices = va_arg(va, IMG_BOOL);
        ui32DeviceIndex = va_arg(va, IMG_UINT32);
        eNewPowerState = va_arg(va, PVRSRV_DEV_POWER_STATE);
@@ -242,7 +377,7 @@ static PVRSRV_ERROR PVRSRVDevicePostPowerStateKM_AnyVaCb(PVRSRV_POWER_DEV *psPow
 
                if (psPowerDevice->eCurrentPowerState != eNewDevicePowerState)
                {
-                       
+                       /* Do any required system-layer processing. */
                        eError = SysDevicePostPowerState(psPowerDevice->ui32DeviceIndex,
                                                                                         eNewDevicePowerState,
                                                                                         psPowerDevice->eCurrentPowerState);
@@ -253,7 +388,7 @@ static PVRSRV_ERROR PVRSRVDevicePostPowerStateKM_AnyVaCb(PVRSRV_POWER_DEV *psPow
 
                        if (psPowerDevice->pfnPostPower != IMG_NULL)
                        {
-                               
+                               /* Call the device's power callback. */
                                eError = psPowerDevice->pfnPostPower(psPowerDevice->hDevCookie,
                                                                                                         eNewDevicePowerState,
                                                                                                         psPowerDevice->eCurrentPowerState);
@@ -269,6 +404,23 @@ static PVRSRV_ERROR PVRSRVDevicePostPowerStateKM_AnyVaCb(PVRSRV_POWER_DEV *psPow
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDevicePostPowerStateKM
+
+ @Description
+
+ Perform device-specific processing required after a power transition
+
+ @Input                bAllDevices : IMG_TRUE - All devices
+                                                 IMG_FALSE - Use ui32DeviceIndex
+ @Input                ui32DeviceIndex : device index
+ @Input                eNewPowerState : New power state
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 static
 PVRSRV_ERROR PVRSRVDevicePostPowerStateKM(IMG_BOOL                                     bAllDevices,
                                                                                  IMG_UINT32                            ui32DeviceIndex,
@@ -279,7 +431,7 @@ PVRSRV_ERROR PVRSRVDevicePostPowerStateKM(IMG_BOOL                                  bAllDevices,
 
        SysAcquireData(&psSysData);
 
-       
+       /* Loop through the power devices. */
        eError = List_PVRSRV_POWER_DEV_PVRSRV_ERROR_Any_va(psSysData->psPowerDeviceList,
                                                                                                                &PVRSRVDevicePostPowerStateKM_AnyVaCb,
                                                                                                                bAllDevices,
@@ -290,30 +442,38 @@ PVRSRV_ERROR PVRSRVDevicePostPowerStateKM(IMG_BOOL                                        bAllDevices,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSetDevicePowerStateKM
+
+ @Description  Set the Device into a new state
+
+ @Input                ui32DeviceIndex : device index
+ @Input                eNewPowerState : New power state
+ @Input                ui32CallerID : KERNEL_ID or ISR_ID
+ @Input                bRetainMutex : If true, the power mutex is retained on exit
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVSetDevicePowerStateKM(IMG_UINT32                            ui32DeviceIndex,
-                                                                                PVRSRV_DEV_POWER_STATE eNewPowerState,
-                                                                                IMG_UINT32                             ui32CallerID,
-                                                                                IMG_BOOL                               bRetainMutex)
+                                                                                PVRSRV_DEV_POWER_STATE eNewPowerState)
 {
        PVRSRV_ERROR    eError;
        SYS_DATA                *psSysData;
 
        SysAcquireData(&psSysData);
 
-       eError = PVRSRVPowerLock(ui32CallerID, IMG_FALSE);
-       if(eError != PVRSRV_OK)
-       {
-               return eError;
-       }
-
        #if defined(PDUMP)
        if (eNewPowerState == PVRSRV_DEV_POWER_STATE_DEFAULT)
        {
-               
-
-
-
+               /*
+                       Pdump a power-up regardless of the default state.
+                       Then disable pdump and transition to the default power state.
+                       This ensures that a power-up is always present in the pdump when necessary.
+               */
                eError = PVRSRVDevicePrePowerStateKM(IMG_FALSE, ui32DeviceIndex, PVRSRV_DEV_POWER_STATE_ON);
                if(eError != PVRSRV_OK)
                {
@@ -329,7 +489,7 @@ PVRSRV_ERROR PVRSRVSetDevicePowerStateKM(IMG_UINT32                         ui32DeviceIndex,
 
                PDUMPSUSPEND();
        }
-       #endif 
+       #endif /* PDUMP */
 
        eError = PVRSRVDevicePrePowerStateKM(IMG_FALSE, ui32DeviceIndex, eNewPowerState);
        if(eError != PVRSRV_OK)
@@ -356,15 +516,22 @@ Exit:
                                "PVRSRVSetDevicePowerStateKM : Transition to %d FAILED 0x%x", eNewPowerState, eError));
        }
 
-       if (!bRetainMutex || (eError != PVRSRV_OK))
-       {
-               PVRSRVPowerUnlock(ui32CallerID);
-       }
-
        return eError;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSystemPrePowerStateKM
+
+ @Description  Perform processing required before a system power transition
+
+ @Input                eNewSysPowerState :
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVSystemPrePowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerState)
 {
@@ -374,7 +541,7 @@ PVRSRV_ERROR PVRSRVSystemPrePowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerStat
 
        SysAcquireData(&psSysData);
 
-       
+       /* This mutex is unlocked in PVRSRVSystemPostPowerStateKM() */
        eError = PVRSRVPowerLock(KERNEL_ID, IMG_TRUE);
        if(eError != PVRSRV_OK)
        {
@@ -386,7 +553,7 @@ PVRSRV_ERROR PVRSRVSystemPrePowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerStat
        {
                if (_IsSystemStatePowered(eNewSysPowerState))
                {
-                       
+                       /* Return device back to its default state. */
                        eNewDevicePowerState = PVRSRV_DEV_POWER_STATE_DEFAULT;
                }
                else
@@ -394,7 +561,7 @@ PVRSRV_ERROR PVRSRVSystemPrePowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerStat
                        eNewDevicePowerState = PVRSRV_DEV_POWER_STATE_OFF;
                }
 
-               
+               /* Perform device-specific transitions. */
                eError = PVRSRVDevicePrePowerStateKM(IMG_TRUE, 0, eNewDevicePowerState);
                if (eError != PVRSRV_OK)
                {
@@ -404,7 +571,7 @@ PVRSRV_ERROR PVRSRVSystemPrePowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerStat
 
        if (eNewSysPowerState != psSysData->eCurrentPowerState)
        {
-               
+               /* Perform system-specific power transitions. */
                eError = SysSystemPrePowerState(eNewSysPowerState);
                if (eError != PVRSRV_OK)
                {
@@ -420,7 +587,7 @@ ErrorExit:
                        "PVRSRVSystemPrePowerStateKM: Transition from %d to %d FAILED 0x%x",
                        psSysData->eCurrentPowerState, eNewSysPowerState, eError));
 
-       
+       /* save the power state for the re-attempt */
        psSysData->eFailedPowerState = eNewSysPowerState;
 
        PVRSRVPowerUnlock(KERNEL_ID);
@@ -429,6 +596,18 @@ ErrorExit:
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSystemPostPowerStateKM
+
+ @Description  Perform processing required after a system power transition
+
+ @Input                eNewSysPowerState :
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVSystemPostPowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerState)
 {
@@ -440,7 +619,7 @@ PVRSRV_ERROR PVRSRVSystemPostPowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerSta
 
        if (eNewSysPowerState != psSysData->eCurrentPowerState)
        {
-               
+               /* Perform system-specific power transitions. */
                eError = SysSystemPostPowerState(eNewSysPowerState);
                if (eError != PVRSRV_OK)
                {
@@ -453,7 +632,7 @@ PVRSRV_ERROR PVRSRVSystemPostPowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerSta
        {
                if (_IsSystemStatePowered(eNewSysPowerState))
                {
-                       
+                       /* Return device back to its default state. */
                        eNewDevicePowerState = PVRSRV_DEV_POWER_STATE_DEFAULT;
                }
                else
@@ -461,7 +640,7 @@ PVRSRV_ERROR PVRSRVSystemPostPowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerSta
                        eNewDevicePowerState = PVRSRV_DEV_POWER_STATE_OFF;
                }
 
-               
+               /* Perform device-specific power transitions. */
                eError = PVRSRVDevicePostPowerStateKM(IMG_TRUE, 0, eNewDevicePowerState);
                if (eError != PVRSRV_OK)
                {
@@ -479,13 +658,14 @@ Exit:
 
        PVRSRVPowerUnlock(KERNEL_ID);
 
-        
+       /* PRQA S 3415 2 */ /* side effects desired */
        if (_IsSystemStatePowered(eNewSysPowerState) &&
                        PVRSRVGetInitServerState(PVRSRV_INIT_SERVER_SUCCESSFUL))
        {
-               
-
-
+               /*
+                       Reprocess the devices' queues in case commands were blocked during
+                       the power transition.
+               */
                PVRSRVScheduleDeviceCallbacks();
        }
 
@@ -493,6 +673,18 @@ Exit:
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSetPowerStateKM
+
+ @Description  Set the system into a new state
+
+ @Input                eNewPowerState :
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVSetPowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerState)
 {
@@ -513,7 +705,7 @@ PVRSRV_ERROR PVRSRVSetPowerStateKM(PVRSRV_SYS_POWER_STATE eNewSysPowerState)
                goto ErrorExit;
        }
 
-       
+       /* save new power state */
        psSysData->eFailedPowerState = PVRSRV_SYS_POWER_STATE_Unspecified;
 
        return PVRSRV_OK;
@@ -524,13 +716,35 @@ ErrorExit:
                        "PVRSRVSetPowerStateKM: Transition from %d to %d FAILED 0x%x",
                        psSysData->eCurrentPowerState, eNewSysPowerState, eError));
 
-       
+       /* save the power state for the re-attempt */
        psSysData->eFailedPowerState = eNewSysPowerState;
 
        return eError;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRegisterPowerDevice
+
+ @Description
+
+ Registers a device with the power manager.  Passes Pre/Post Power handlers
+ and private device handle to be passed to power handlers
+
+ @Input                ui32DeviceIndex : device index
+ @Input                pfnPrePower : Pre power transition handler
+ @Input                pfnPostPower : Post power transition handler
+ @Input                pfnPreClockSpeedChange : Pre clock speed transition handler (if required)
+ @Input                pfnPostClockSpeedChange : Post clock speed transition handler (if required)
+ @Input                hDevCookie : Dev cookie for dev power handlers
+ @Input                eCurrentPowerState : Current power state of the device
+ @Input                eDefaultPowerState : Default power state of the device
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVRegisterPowerDevice(IMG_UINT32                                      ui32DeviceIndex,
                                                                           PFN_PRE_POWER                                pfnPrePower,
                                                                           PFN_POST_POWER                               pfnPostPower,
@@ -562,7 +776,7 @@ PVRSRV_ERROR PVRSRVRegisterPowerDevice(IMG_UINT32                                   ui32DeviceIndex,
                return eError;
        }
 
-       
+       /* setup device for power manager */
        psPowerDevice->pfnPrePower = pfnPrePower;
        psPowerDevice->pfnPostPower = pfnPostPower;
        psPowerDevice->pfnPreClockSpeedChange = pfnPreClockSpeedChange;
@@ -572,13 +786,27 @@ PVRSRV_ERROR PVRSRVRegisterPowerDevice(IMG_UINT32                                 ui32DeviceIndex,
        psPowerDevice->eCurrentPowerState = eCurrentPowerState;
        psPowerDevice->eDefaultPowerState = eDefaultPowerState;
 
-       
+       /* insert into power device list */
        List_PVRSRV_POWER_DEV_Insert(&(psSysData->psPowerDeviceList), psPowerDevice);
 
        return (PVRSRV_OK);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRemovePowerDevice
+
+ @Description
+
+ Removes device from power management register. Device is located by Device Index
+
+ @Input                ui32DeviceIndex : device index
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVRemovePowerDevice (IMG_UINT32 ui32DeviceIndex)
 {
        SYS_DATA                        *psSysData;
@@ -586,7 +814,7 @@ PVRSRV_ERROR PVRSRVRemovePowerDevice (IMG_UINT32 ui32DeviceIndex)
 
        SysAcquireData(&psSysData);
 
-       
+       /* find device in list and remove it */
        psPowerDev = (PVRSRV_POWER_DEV*)
                                        List_PVRSRV_POWER_DEV_Any_va(psSysData->psPowerDeviceList,
                                                                                                 &MatchPowerDeviceIndex_AnyVaCb,
@@ -596,13 +824,27 @@ PVRSRV_ERROR PVRSRVRemovePowerDevice (IMG_UINT32 ui32DeviceIndex)
        {
                List_PVRSRV_POWER_DEV_Remove(psPowerDev);
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_POWER_DEV), psPowerDev, IMG_NULL);
-               
+               /*not nulling pointer, copy on stack*/
        }
 
        return (PVRSRV_OK);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVIsDevicePowered
+
+ @Description
+
+       Whether the device is powered, for the purposes of lockup detection.
+
+ @Input                ui32DeviceIndex : device index
+
+ @Return       IMG_BOOL
+
+******************************************************************************/
 IMG_EXPORT
 IMG_BOOL PVRSRVIsDevicePowered(IMG_UINT32 ui32DeviceIndex)
 {
@@ -611,7 +853,7 @@ IMG_BOOL PVRSRVIsDevicePowered(IMG_UINT32 ui32DeviceIndex)
 
        SysAcquireData(&psSysData);
 
-        
+       /* PRQA S 3415 2 */ /* order not important */
        if (OSIsResourceLocked(&psSysData->sPowerStateChangeResource, KERNEL_ID) ||
                OSIsResourceLocked(&psSysData->sPowerStateChangeResource, ISR_ID))
        {
@@ -627,6 +869,22 @@ IMG_BOOL PVRSRVIsDevicePowered(IMG_UINT32 ui32DeviceIndex)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDevicePreClockSpeedChange
+
+ @Description
+
+       Notification from system layer that a device clock speed change is about to happen.
+
+ @Input                ui32DeviceIndex : device index
+ @Input                bIdleDevice : whether the device should be idled
+ @Input                pvInfo
+
+ @Return       IMG_VOID
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVDevicePreClockSpeedChange(IMG_UINT32        ui32DeviceIndex,
                                                                                         IMG_BOOL       bIdleDevice,
                                                                                         IMG_VOID       *pvInfo)
@@ -641,7 +899,7 @@ PVRSRV_ERROR PVRSRVDevicePreClockSpeedChange(IMG_UINT32     ui32DeviceIndex,
 
        if (bIdleDevice)
        {
-               
+               /* This mutex is released in PVRSRVDevicePostClockSpeedChange. */
                eError = PVRSRVPowerLock(KERNEL_ID, IMG_FALSE);
                if (eError != PVRSRV_OK)
                {
@@ -650,7 +908,7 @@ PVRSRV_ERROR PVRSRVDevicePreClockSpeedChange(IMG_UINT32     ui32DeviceIndex,
                }
        }
 
-       
+       /*search the device and then do the pre clock speed change*/
        psPowerDevice = (PVRSRV_POWER_DEV*)
                                        List_PVRSRV_POWER_DEV_Any_va(psSysData->psPowerDeviceList,
                                                                                                 &MatchPowerDeviceIndex_AnyVaCb,
@@ -678,6 +936,22 @@ PVRSRV_ERROR PVRSRVDevicePreClockSpeedChange(IMG_UINT32    ui32DeviceIndex,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDevicePostClockSpeedChange
+
+ @Description
+
+       Notification from system layer that a device clock speed change has just happened.
+
+ @Input                ui32DeviceIndex : device index
+ @Input                bIdleDevice : whether the device had been idled
+ @Input                pvInfo
+
+ @Return       IMG_VOID
+
+******************************************************************************/
 IMG_VOID PVRSRVDevicePostClockSpeedChange(IMG_UINT32   ui32DeviceIndex,
                                                                                  IMG_BOOL              bIdleDevice,
                                                                                  IMG_VOID              *pvInfo)
@@ -690,7 +964,7 @@ IMG_VOID PVRSRVDevicePostClockSpeedChange(IMG_UINT32        ui32DeviceIndex,
 
        SysAcquireData(&psSysData);
 
-       
+       /*search the device and then do the post clock speed change*/
        psPowerDevice = (PVRSRV_POWER_DEV*)
                                        List_PVRSRV_POWER_DEV_Any_va(psSysData->psPowerDeviceList,
                                                                                                 &MatchPowerDeviceIndex_AnyVaCb,
@@ -712,8 +986,11 @@ IMG_VOID PVRSRVDevicePostClockSpeedChange(IMG_UINT32       ui32DeviceIndex,
 
        if (bIdleDevice)
        {
-               
+               /* This mutex was acquired in PVRSRVDevicePreClockSpeedChange. */
                PVRSRVPowerUnlock(KERNEL_ID);
        }
 }
 
+/******************************************************************************
+ End of file (power.c)
+******************************************************************************/
index 6feccd2..d0f7f6b 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          core services functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Main APIs for core services functions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
 #include "buffer_manager.h"
@@ -35,6 +51,7 @@
 #if defined(TTRACE)
 #include "ttrace.h"
 #endif
+#include "perfkm.h"
 
 #include "pvrversion.h"
 
 
 IMG_UINT32     g_ui32InitFlags;
 
+/* mark which parts of Services were initialised */
 #define                INIT_DATA_ENABLE_PDUMPINIT      0x1U
 #define                INIT_DATA_ENABLE_TTARCE         0x2U
 
+/*!
+******************************************************************************
+
+ @Function     AllocateDeviceID
+
+ @Description
+
+ allocates a device id from the pool of valid ids
+
+ @input psSysData :    system data
+
+ @input pui32DevID : device id to return
+
+ @Return device id
+
+******************************************************************************/
 PVRSRV_ERROR AllocateDeviceID(SYS_DATA *psSysData, IMG_UINT32 *pui32DevID)
 {
        SYS_DEVICE_ID* psDeviceWalker;
@@ -53,7 +87,7 @@ PVRSRV_ERROR AllocateDeviceID(SYS_DATA *psSysData, IMG_UINT32 *pui32DevID)
        psDeviceWalker = &psSysData->sDeviceID[0];
        psDeviceEnd = psDeviceWalker + psSysData->ui32NumDevices;
 
-       
+       /* find a free ID */
        while (psDeviceWalker < psDeviceEnd)
        {
                if (!psDeviceWalker->bInUse)
@@ -67,13 +101,29 @@ PVRSRV_ERROR AllocateDeviceID(SYS_DATA *psSysData, IMG_UINT32 *pui32DevID)
 
        PVR_DPF((PVR_DBG_ERROR,"AllocateDeviceID: No free and valid device IDs available!"));
 
-       
+       /* Should never get here: sDeviceID[] may have been setup too small */
        PVR_ASSERT(psDeviceWalker < psDeviceEnd);
 
        return PVRSRV_ERROR_NO_FREE_DEVICEIDS_AVALIABLE;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     FreeDeviceID
+
+ @Description
+
+ frees a device id from the pool of valid ids
+
+ @input psSysData :    system data
+
+ @input ui32DevID : device id to free
+
+ @Return device id
+
+******************************************************************************/
 PVRSRV_ERROR FreeDeviceID(SYS_DATA *psSysData, IMG_UINT32 ui32DevID)
 {
        SYS_DEVICE_ID* psDeviceWalker;
@@ -82,10 +132,10 @@ PVRSRV_ERROR FreeDeviceID(SYS_DATA *psSysData, IMG_UINT32 ui32DevID)
        psDeviceWalker = &psSysData->sDeviceID[0];
        psDeviceEnd = psDeviceWalker + psSysData->ui32NumDevices;
 
-       
+       /* find the ID to free */
        while (psDeviceWalker < psDeviceEnd)
        {
-               
+               /* if matching id and in use, free */
                if      (
                                (psDeviceWalker->uiID == ui32DevID) &&
                                (psDeviceWalker->bInUse)
@@ -99,13 +149,29 @@ PVRSRV_ERROR FreeDeviceID(SYS_DATA *psSysData, IMG_UINT32 ui32DevID)
 
        PVR_DPF((PVR_DBG_ERROR,"FreeDeviceID: no matching dev ID that is in use!"));
 
-       
+       /* should never get here */
        PVR_ASSERT(psDeviceWalker < psDeviceEnd);
 
        return PVRSRV_ERROR_INVALID_DEVICEID;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     ReadHWReg
+
+ @Description
+
+ register access function
+
+ @input pvLinRegBaseAddr :     lin addr of register block base
+
+ @input ui32Offset :    byte offset from register base
+
+ @Return   register value
+
+******************************************************************************/
 #ifndef ReadHWReg
 IMG_EXPORT
 IMG_UINT32 ReadHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset)
@@ -115,6 +181,24 @@ IMG_UINT32 ReadHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset)
 #endif
 
 
+/*!
+******************************************************************************
+
+ @Function     WriteHWReg
+
+ @Description
+
+ register access function
+
+ @input pvLinRegBaseAddr :     lin addr of register block base
+
+ @input ui32Offset :    byte offset from register base
+
+ @input ui32Value :     value to write to register
+
+ @Return   register value : original reg. value
+
+******************************************************************************/
 #ifndef WriteHWReg
 IMG_EXPORT
 IMG_VOID WriteHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset, IMG_UINT32 ui32Value)
@@ -127,6 +211,24 @@ IMG_VOID WriteHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset, IMG_UINT3
 #endif
 
 
+/*!
+******************************************************************************
+
+ @Function     WriteHWRegs
+
+ @Description
+
+ register access function
+
+ @input pvLinRegBaseAddr :     lin addr of register block base
+
+ @input ui32Count :     register count
+
+ @input psHWRegs :      address/value register list
+
+ @Return   none
+
+******************************************************************************/
 #ifndef WriteHWRegs
 IMG_EXPORT
 IMG_VOID WriteHWRegs(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Count, PVRSRV_HWREG *psHWRegs)
@@ -140,6 +242,19 @@ IMG_VOID WriteHWRegs(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Count, PVRSRV_HW
 }
 #endif
 
+/*!
+******************************************************************************
+ @Function     PVRSRVEnumerateDCKM_ForEachVaCb
+
+ @Description
+
+ Enumerates the device node (if is of the same class as given).
+
+ @Input psDeviceNode   - The device node to be enumerated
+               va                              - variable arguments list, with:
+                                                       pui32DevCount   - The device count pointer (to be increased)
+                                                       ppui32DevID             - The pointer to the device IDs pointer (to be updated and increased)
+******************************************************************************/
 static IMG_VOID PVRSRVEnumerateDevicesKM_ForEachVaCb(PVRSRV_DEVICE_NODE *psDeviceNode, va_list va)
 {
        IMG_UINT *pui32DevCount;
@@ -158,11 +273,43 @@ static IMG_VOID PVRSRVEnumerateDevicesKM_ForEachVaCb(PVRSRV_DEVICE_NODE *psDevic
 
 
 
+/*!
+******************************************************************************
+
+ @Function PVRSRVEnumerateDevicesKM
+
+ @Description
+ This function will enumerate all the devices supported by the
+ PowerVR services within the target system.
+ The function returns a list of the device ID strcutres stored either in
+ the services or constructed in the user mode glue component in certain
+ environments. The number of devices in the list is also returned.
+
+ In a binary layered component which does not support dynamic runtime selection,
+ the glue code should compile to return the supported devices statically,
+ e.g. multiple instances of the same device if multiple devices are supported,
+ or the target combination of MBX and display device.
+
+ In the case of an environment (for instance) where one MBX1 may connect to two
+ display devices this code would enumerate all three devices and even
+ non-dynamic MBX1 selection code should retain the facility to parse the list
+ to find the index of the MBX device
+
+ @output pui32NumDevices :     On success, contains the number of devices present
+                                                       in the system
+
+ @output psDevIdList    :      Pointer to called supplied buffer to receive the
+                                                       list of PVRSRV_DEVICE_IDENTIFIER
+
+ @return PVRSRV_ERROR  :       PVRSRV_NO_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVEnumerateDevicesKM(IMG_UINT32 *pui32NumDevices,
                                                                                                   PVRSRV_DEVICE_IDENTIFIER *psDevIdList)
 {
        SYS_DATA                        *psSysData;
+/*     PVRSRV_DEVICE_NODE      *psDeviceNode; */
        IMG_UINT32                      i;
 
        if (!pui32NumDevices || !psDevIdList)
@@ -173,20 +320,22 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVEnumerateDevicesKM(IMG_UINT32 *pui32NumDevices,
 
        SysAcquireData(&psSysData);
 
-       
-
+       /*
+               setup input buffer to be `empty'
+       */
        for (i=0; i<PVRSRV_MAX_DEVICES; i++)
        {
                psDevIdList[i].eDeviceType = PVRSRV_DEVICE_TYPE_UNKNOWN;
        }
 
-       
+       /* and zero device count */
        *pui32NumDevices = 0;
 
-       
-
-
-
+       /*
+               Search through the device list for services managed devices
+               return id info for each device and the number of devices
+               available
+       */
        List_PVRSRV_DEVICE_NODE_ForEach_va(psSysData->psDeviceNodeList,
                                                                           &PVRSRVEnumerateDevicesKM_ForEachVaCb,
                                                                           pui32NumDevices,
@@ -197,11 +346,23 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVEnumerateDevicesKM(IMG_UINT32 *pui32NumDevices,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVInit
+
+ @Description  Initialise services
+
+ @Input           psSysData    : sysdata structure
+
+ @Return   PVRSRV_ERROR        :
+
+******************************************************************************/
 PVRSRV_ERROR IMG_CALLCONV PVRSRVInit(PSYS_DATA psSysData)
 {
        PVRSRV_ERROR    eError;
 
-       
+       /* Initialise Resource Manager */
        eError = ResManInit();
        if (eError != PVRSRV_OK)
        {
@@ -214,25 +375,25 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInit(PSYS_DATA psSysData)
                goto Error;
        }
 
-       
+       /* Initialise handles */
        eError = PVRSRVHandleInit();
        if(eError != PVRSRV_OK)
        {
                goto Error;
        }
 
-       
+       /* Initialise Power Manager Lock */
        eError = OSCreateResource(&psSysData->sPowerStateChangeResource);
        if (eError != PVRSRV_OK)
        {
                goto Error;
        }
 
-       
+       /* Initialise system power state */
        psSysData->eCurrentPowerState = PVRSRV_SYS_POWER_STATE_D0;
        psSysData->eFailedPowerState = PVRSRV_SYS_POWER_STATE_Unspecified;
 
-       
+       /* Create an event object */
        if(OSAllocMem( PVRSRV_PAGEABLE_SELECT,
                                         sizeof(PVRSRV_EVENTOBJECT) ,
                                         (IMG_VOID **)&psSysData->psGlobalEventObject, 0,
@@ -247,7 +408,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInit(PSYS_DATA psSysData)
                goto Error;
        }
 
-       
+       /* Store OS high res timer fallbacks, the system is free to overide these */
        psSysData->pfnHighResTimerCreate = OSFuncHighResTimerCreate;
        psSysData->pfnHighResTimerGetus = OSFuncHighResTimerGetus;
        psSysData->pfnHighResTimerDestroy = OSFuncHighResTimerDestroy;
@@ -259,10 +420,11 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInit(PSYS_DATA psSysData)
        g_ui32InitFlags |= INIT_DATA_ENABLE_TTARCE;
 #endif
 
-       
+       /* Initialise pdump */
        PDUMPINIT();
        g_ui32InitFlags |= INIT_DATA_ENABLE_PDUMPINIT;
 
+       PERFINIT();
        return eError;
 
 Error:
@@ -272,6 +434,18 @@ Error:
 
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDeInit
+
+ @Description  De-Initialise services
+
+ @Input           psSysData    : sysdata structure
+
+ @Return   PVRSRV_ERROR        :
+
+******************************************************************************/
 IMG_VOID IMG_CALLCONV PVRSRVDeInit(PSYS_DATA psSysData)
 {
        PVRSRV_ERROR    eError;
@@ -283,20 +457,23 @@ IMG_VOID IMG_CALLCONV PVRSRVDeInit(PSYS_DATA psSysData)
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVDeInit: PVRSRVHandleDeInit failed - invalid param"));
                return;
        }
+
+       PERFDEINIT();
+
 #if defined(TTRACE)
-       
+       /* deinitialise ttrace */
        if ((g_ui32InitFlags & INIT_DATA_ENABLE_TTARCE) > 0)
        {
                PVRSRVTimeTraceDeinit();
        }
 #endif
-       
+       /* deinitialise pdump */
        if( (g_ui32InitFlags & INIT_DATA_ENABLE_PDUMPINIT) > 0)
        {
                PDUMPDEINIT();
        }
        
-       
+       /* destroy event object */
        if(psSysData->psGlobalEventObject)
        {
                OSEventObjectDestroyKM(psSysData->psGlobalEventObject);
@@ -323,6 +500,26 @@ IMG_VOID IMG_CALLCONV PVRSRVDeInit(PSYS_DATA psSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRegisterDevice
+
+ @Description
+
+ registers a device with the system
+
+ @Input           psSysData                    : sysdata structure
+
+ @Input           pfnRegisterDevice    : device registration function
+
+ @Input           ui32SOCInterruptBit  : SoC interrupt bit for this device
+
+ @Output       pui32DeviceIndex                : unique device key (for case of multiple identical devices)
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 PVRSRV_ERROR IMG_CALLCONV PVRSRVRegisterDevice(PSYS_DATA psSysData,
                                                                                          PVRSRV_ERROR (*pfnRegisterDevice)(PVRSRV_DEVICE_NODE*),
                                                                                          IMG_UINT32 ui32SOCInterruptBit,
@@ -331,7 +528,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVRegisterDevice(PSYS_DATA psSysData,
        PVRSRV_ERROR            eError;
        PVRSRV_DEVICE_NODE      *psDeviceNode;
 
-       
+       /* Allocate device node */
        if(OSAllocMem( PVRSRV_OS_NON_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_DEVICE_NODE),
                                         (IMG_VOID **)&psDeviceNode, IMG_NULL,
@@ -347,33 +544,48 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVRegisterDevice(PSYS_DATA psSysData,
        {
                OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                        sizeof(PVRSRV_DEVICE_NODE), psDeviceNode, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVRegisterDevice : Failed to register device"));
                return (PVRSRV_ERROR_DEVICE_REGISTER_FAILED);
        }
 
-       
-
-
-
-
+       /*
+               make the refcount 1 and test on this to initialise device
+               at acquiredevinfo. On release if refcount is 1, deinitialise
+               and when refcount is 0 (sysdata de-alloc) deallocate the device
+               structures
+       */
        psDeviceNode->ui32RefCount = 1;
        psDeviceNode->psSysData = psSysData;
        psDeviceNode->ui32SOCInterruptBit = ui32SOCInterruptBit;
 
-       
+       /* all devices need a unique identifier */
        AllocateDeviceID(psSysData, &psDeviceNode->sDevId.ui32DeviceIndex);
 
-       
+       /* and finally insert the device into the dev-list */
        List_PVRSRV_DEVICE_NODE_Insert(&psSysData->psDeviceNodeList, psDeviceNode);
 
-       
+       /* and copy back index */
        *pui32DeviceIndex = psDeviceNode->sDevId.ui32DeviceIndex;
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVInitialiseDevice
+
+ @Description
+
+ initialises device by index
+
+ @Input           ui32DevIndex : Index to the required device
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 PVRSRV_ERROR IMG_CALLCONV PVRSRVInitialiseDevice (IMG_UINT32 ui32DevIndex)
 {
        PVRSRV_DEVICE_NODE      *psDeviceNode;
@@ -384,7 +596,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInitialiseDevice (IMG_UINT32 ui32DevIndex)
 
        SysAcquireData(&psSysData);
 
-       
+       /* Find device in the list */
        psDeviceNode = (PVRSRV_DEVICE_NODE*)
                                         List_PVRSRV_DEVICE_NODE_Any_va(psSysData->psDeviceNodeList,
                                                                                                        &MatchDeviceKM_AnyVaCb,
@@ -392,14 +604,19 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInitialiseDevice (IMG_UINT32 ui32DevIndex)
                                                                                                        IMG_TRUE);
        if(!psDeviceNode)
        {
-               
+               /* Devinfo not in the list */
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVInitialiseDevice: requested device is not present"));
                return PVRSRV_ERROR_INIT_FAILURE;
        }
-       PVR_ASSERT (psDeviceNode->ui32RefCount > 0);
+/*
+FoundDevice:
+*/
 
-       
+       PVR_ASSERT (psDeviceNode->ui32RefCount > 0);
 
+       /*
+               Create the device's resource manager context.
+       */
        eError = PVRSRVResManConnect(IMG_NULL, &psDeviceNode->hResManContext);
        if (eError != PVRSRV_OK)
        {
@@ -407,7 +624,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInitialiseDevice (IMG_UINT32 ui32DevIndex)
                return eError;
        }
 
-       
+       /* Initialise the device */
        if(psDeviceNode->pfnInitDevice != IMG_NULL)
        {
                eError = psDeviceNode->pfnInitDevice(psDeviceNode);
@@ -425,9 +642,17 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInitialiseDevice (IMG_UINT32 ui32DevIndex)
 static PVRSRV_ERROR PVRSRVFinaliseSystem_SetPowerState_AnyCb(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        PVRSRV_ERROR eError;
+
+       eError = PVRSRVPowerLock(KERNEL_ID, IMG_FALSE);
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVFinaliseSystem: Failed PVRSRVPowerLock call (device index: %d)", psDeviceNode->sDevId.ui32DeviceIndex));
+               return eError;
+       }
+
        eError = PVRSRVSetDevicePowerStateKM(psDeviceNode->sDevId.ui32DeviceIndex,
-                                                                                PVRSRV_DEV_POWER_STATE_DEFAULT,
-                                                                                KERNEL_ID, IMG_FALSE);
+                                                                                PVRSRV_DEV_POWER_STATE_DEFAULT);
+       PVRSRVPowerUnlock(KERNEL_ID);
        if (eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVFinaliseSystem: Failed PVRSRVSetDevicePowerStateKM call (device index: %d)", psDeviceNode->sDevId.ui32DeviceIndex));
@@ -435,6 +660,7 @@ static PVRSRV_ERROR PVRSRVFinaliseSystem_SetPowerState_AnyCb(PVRSRV_DEVICE_NODE
        return eError;
 }
 
+/*wraps the PVRSRVDevInitCompatCheck call and prints a debugging message if failed*/
 static PVRSRV_ERROR PVRSRVFinaliseSystem_CompatCheck_AnyCb(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        PVRSRV_ERROR eError;
@@ -447,8 +673,23 @@ static PVRSRV_ERROR PVRSRVFinaliseSystem_CompatCheck_AnyCb(PVRSRV_DEVICE_NODE *p
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVFinaliseSystem
+
+ @Description
+
+ Final part of system initialisation.
+
+ @Input           ui32DevIndex : Index to the required device
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 PVRSRV_ERROR IMG_CALLCONV PVRSRVFinaliseSystem(IMG_BOOL bInitSuccessful)
 {
+/*     PVRSRV_DEVICE_NODE      *psDeviceNode;*/
        SYS_DATA                *psSysData;
        PVRSRV_ERROR            eError;
 
@@ -465,7 +706,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVFinaliseSystem(IMG_BOOL bInitSuccessful)
                        return eError;
                }
 
-               
+               /* Place all devices into their default power state. */
                eError = List_PVRSRV_DEVICE_NODE_PVRSRV_ERROR_Any(psSysData->psDeviceNodeList,
                                                                                                                &PVRSRVFinaliseSystem_SetPowerState_AnyCb);
                if (eError != PVRSRV_OK)
@@ -473,7 +714,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVFinaliseSystem(IMG_BOOL bInitSuccessful)
                        return eError;
                }
 
-               
+               /* Verify microkernel compatibility for devices */
                eError = List_PVRSRV_DEVICE_NODE_PVRSRV_ERROR_Any(psSysData->psDeviceNodeList,
                                                                                                        &PVRSRVFinaliseSystem_CompatCheck_AnyCb);
                if (eError != PVRSRV_OK)
@@ -482,13 +723,8 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVFinaliseSystem(IMG_BOOL bInitSuccessful)
                }
        }
 
-       
-
-
-
-#if !defined(__QNXNTO__)
+       /* Some platforms call this too early in the boot phase. */
        PDUMPENDINITPHASE();
-#endif
 
        return PVRSRV_OK;
 }
@@ -496,13 +732,34 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVFinaliseSystem(IMG_BOOL bInitSuccessful)
 
 PVRSRV_ERROR PVRSRVDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
-       
+       /* Only check devices which specify a compatibility check callback */
        if (psDeviceNode->pfnInitDeviceCompatCheck)
                return psDeviceNode->pfnInitDeviceCompatCheck(psDeviceNode);
        else
                return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVAcquireDeviceDataKM
+
+ @Description
+
+ Matchs a device given a device type and a device index.
+
+ @input        psDeviceNode :The device node to be matched.
+
+ @Input           va : Variable argument list with:
+                       eDeviceType : Required device type. If type is unknown use ui32DevIndex
+                                                to locate device data
+
+                       ui32DevIndex : Index to the required device obtained from the
+                                               PVRSRVEnumerateDevice function
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 static IMG_VOID * PVRSRVAcquireDeviceDataKM_Match_AnyVaCb(PVRSRV_DEVICE_NODE *psDeviceNode, va_list va)
 {
        PVRSRV_DEVICE_TYPE eDeviceType;
@@ -524,6 +781,27 @@ static IMG_VOID * PVRSRVAcquireDeviceDataKM_Match_AnyVaCb(PVRSRV_DEVICE_NODE *ps
        }
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVAcquireDeviceDataKM
+
+ @Description
+
+ Returns device information
+
+ @Input           ui32DevIndex : Index to the required device obtained from the
+                                               PVRSRVEnumerateDevice function
+
+ @Input           eDeviceType : Required device type. If type is unknown use ui32DevIndex
+                                                to locate device data
+
+ @Output  *phDevCookie : Dev Cookie
+
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVAcquireDeviceDataKM (IMG_UINT32                        ui32DevIndex,
                                                                                                         PVRSRV_DEVICE_TYPE     eDeviceType,
@@ -536,7 +814,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVAcquireDeviceDataKM (IMG_UINT32                     ui32DevIndex,
 
        SysAcquireData(&psSysData);
 
-       
+       /* Find device in the list */
        psDeviceNode = List_PVRSRV_DEVICE_NODE_Any_va(psSysData->psDeviceNodeList,
                                                                                                &PVRSRVAcquireDeviceDataKM_Match_AnyVaCb,
                                                                                                eDeviceType,
@@ -545,14 +823,16 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVAcquireDeviceDataKM (IMG_UINT32                   ui32DevIndex,
 
        if (!psDeviceNode)
        {
-               
+               /* device can't be found in the list so it isn't in the system */
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVAcquireDeviceDataKM: requested device is not present"));
                return PVRSRV_ERROR_INIT_FAILURE;
        }
 
+/*FoundDevice:*/
+
        PVR_ASSERT (psDeviceNode->ui32RefCount > 0);
 
-       
+       /* return the dev cookie? */
        if (phDevCookie)
        {
                *phDevCookie = (IMG_HANDLE)psDeviceNode;
@@ -562,6 +842,20 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVAcquireDeviceDataKM (IMG_UINT32                    ui32DevIndex,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDeinitialiseDevice
+
+ @Description
+
+ This De-inits device
+
+ @Input           ui32DevIndex : Index to the required device
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 PVRSRV_ERROR IMG_CALLCONV PVRSRVDeinitialiseDevice(IMG_UINT32 ui32DevIndex)
 {
        PVRSRV_DEVICE_NODE      *psDeviceNode;
@@ -582,20 +876,28 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDeinitialiseDevice(IMG_UINT32 ui32DevIndex)
                return PVRSRV_ERROR_DEVICEID_NOT_FOUND;
        }
 
-       
+       eError = PVRSRVPowerLock(KERNEL_ID, IMG_FALSE);
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"PVRSRVDeinitialiseDevice: Failed PVRSRVPowerLock call"));
+               return eError;
+       }
 
+       /*
+               Power down the device if necessary.
+        */
        eError = PVRSRVSetDevicePowerStateKM(ui32DevIndex,
-                                                                                PVRSRV_DEV_POWER_STATE_OFF,
-                                                                                KERNEL_ID,
-                                                                                IMG_FALSE);
+                                                                                PVRSRV_DEV_POWER_STATE_OFF);
+       PVRSRVPowerUnlock(KERNEL_ID);
        if (eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVDeinitialiseDevice: Failed PVRSRVSetDevicePowerStateKM call"));
                return eError;
        }
 
-       
-
+       /*
+               Free the dissociated device memory.
+       */
        eError = ResManFreeResByCriteria(psDeviceNode->hResManContext,
                                                                         RESMAN_CRITERIA_RESTYPE,
                                                                         RESMAN_TYPE_DEVICEMEM_ALLOCATION,
@@ -606,8 +908,9 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDeinitialiseDevice(IMG_UINT32 ui32DevIndex)
                return eError;
        }
 
-       
-
+       /*
+               De-init the device.
+       */
        if(psDeviceNode->pfnDeInitDevice != IMG_NULL)
        {
                eError = psDeviceNode->pfnDeInitDevice(psDeviceNode);
@@ -618,19 +921,20 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDeinitialiseDevice(IMG_UINT32 ui32DevIndex)
                }
        }
 
-       
-
+       /*
+               Close the device's resource manager context.
+       */
        PVRSRVResManDisconnect(psDeviceNode->hResManContext, IMG_TRUE);
        psDeviceNode->hResManContext = IMG_NULL;
 
-       
+       /* remove node from list */
        List_PVRSRV_DEVICE_NODE_Remove(psDeviceNode);
 
-       
+       /* deallocate id and memory */
        (IMG_VOID)FreeDeviceID(psSysData, ui32DevIndex);
        OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                sizeof(PVRSRV_DEVICE_NODE), psDeviceNode, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
 
        return (PVRSRV_OK);
 }
@@ -651,8 +955,9 @@ PVRSRV_ERROR IMG_CALLCONV PollForValueKM (volatile IMG_UINT32*      pui32LinMemAddr,
                PVR_UNREFERENCED_PARAMETER(ui32PollPeriodus);
                #endif  
                
-               
-               
+               /* For the Emulator we want the system to stop when a lock-up is detected so the state can be analysed.
+                * Also the Emulator is much slower than real silicon so timeouts are not valid. 
+                */
                do
                {
                        if((*pui32LinMemAddr & ui32Mask) == ui32Value)
@@ -666,18 +971,18 @@ PVRSRV_ERROR IMG_CALLCONV PollForValueKM (volatile IMG_UINT32*    pui32LinMemAddr,
                        OSReleaseThreadQuanta();
                        #endif  
 
-               } while (ui32Timeoutus); 
+               } while (ui32Timeoutus); /* Endless loop only for the Emulator */
        }
 #else
        {
-               IMG_UINT32      ui32ActualValue = 0xFFFFFFFFU; 
+               IMG_UINT32      ui32ActualValue = 0xFFFFFFFFU; /* Initialiser only required to prevent incorrect warning */
 
                if (bAllowPreemption)
                {
                        PVR_ASSERT(ui32PollPeriodus >= 1000);
                }
 
-                
+               /* PRQA S 3415,4109 1 */ /* macro format critical - leave alone */
                LOOP_UNTIL_TIMEOUT(ui32Timeoutus)
                {
                        ui32ActualValue = (*pui32LinMemAddr & ui32Mask);
@@ -699,12 +1004,13 @@ PVRSRV_ERROR IMG_CALLCONV PollForValueKM (volatile IMG_UINT32*   pui32LinMemAddr,
                PVR_DPF((PVR_DBG_ERROR,"PollForValueKM: Timeout. Expected 0x%x but found 0x%x (mask 0x%x).",
                                ui32Value, ui32ActualValue, ui32Mask));
        }
-#endif 
+#endif /* #if defined (EMULATOR) */
 
        return PVRSRV_ERROR_TIMEOUT;
 }
 
 
+/*Level 3 of the loop nesting*/
 static IMG_VOID PVRSRVGetMiscInfoKM_RA_GetStats_ForEachVaCb(BM_HEAP *psBMHeap, va_list va)
 {
        IMG_CHAR **ppszStr;
@@ -716,7 +1022,10 @@ static IMG_VOID PVRSRVGetMiscInfoKM_RA_GetStats_ForEachVaCb(BM_HEAP *psBMHeap, v
        pui32StrLen = va_arg(va, IMG_UINT32*);
        ui32Mode = va_arg(va, IMG_UINT32);
 
-       
+       /* Would be better to pass fn pointer in the variable args list
+        * but MS C compiler complains with error C2066: In ANSI C,
+        * it is not legal to cast between a function pointer and a data pointer.
+        */
        switch(ui32Mode)
        {
                case PVRSRV_MISC_INFO_MEMSTATS_PRESENT:
@@ -744,6 +1053,7 @@ static IMG_VOID PVRSRVGetMiscInfoKM_RA_GetStats_ForEachVaCb(BM_HEAP *psBMHeap, v
        }
 }
 
+/*Level 2 of the loop nesting*/
 static PVRSRV_ERROR PVRSRVGetMiscInfoKM_BMContext_AnyVaCb(BM_CONTEXT *psBMContext, va_list va)
 {
 
@@ -771,6 +1081,7 @@ static PVRSRV_ERROR PVRSRVGetMiscInfoKM_BMContext_AnyVaCb(BM_CONTEXT *psBMContex
 }
 
 
+/*level 1 of the loop nesting*/
 static PVRSRV_ERROR PVRSRVGetMiscInfoKM_Device_AnyVaCb(PVRSRV_DEVICE_NODE *psDeviceNode, va_list va)
 {
        IMG_UINT32 *pui32StrLen;
@@ -787,7 +1098,7 @@ static PVRSRV_ERROR PVRSRVGetMiscInfoKM_Device_AnyVaCb(PVRSRV_DEVICE_NODE *psDev
        *pi32Count = OSSNPrintf(*ppszStr, 100, "\n\nDevice Type %d:\n", psDeviceNode->sDevId.eDeviceType);
        UPDATE_SPACE(*ppszStr, *pi32Count, *pui32StrLen);
 
-       
+       /* kernel context: */
        if(psDeviceNode->sDevMemoryInfo.pBMKernelContext)
        {
                CHECK_SPACE(*pui32StrLen);
@@ -801,7 +1112,7 @@ static PVRSRV_ERROR PVRSRVGetMiscInfoKM_Device_AnyVaCb(PVRSRV_DEVICE_NODE *psDev
                                                                ui32Mode);
        }
 
-       
+       /* double loop app contexts:heaps */
        return List_BM_CONTEXT_PVRSRV_ERROR_Any_va(psDeviceNode->sDevMemoryInfo.pBMContext,
                                                                                                &PVRSRVGetMiscInfoKM_BMContext_AnyVaCb,
                                                                                                pui32StrLen,
@@ -811,6 +1122,19 @@ static PVRSRV_ERROR PVRSRVGetMiscInfoKM_Device_AnyVaCb(PVRSRV_DEVICE_NODE *psDev
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVGetMiscInfoKM
+
+ @Description
+       Retrieves misc. info.
+
+ @Output PVRSRV_MISC_INFO
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO_KM *psMiscInfo)
@@ -828,7 +1152,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
 
        psMiscInfo->ui32StatePresent = 0;
 
-       
+       /* do a basic check for uninitialised request flag */
        if(psMiscInfo->ui32StateRequest & ~(PVRSRV_MISC_INFO_TIMER_PRESENT
                                                                                |PVRSRV_MISC_INFO_CLOCKGATE_PRESENT
                                                                                |PVRSRV_MISC_INFO_MEMSTATS_PRESENT
@@ -836,7 +1160,10 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                                                                                |PVRSRV_MISC_INFO_DDKVERSION_PRESENT
                                                                                |PVRSRV_MISC_INFO_CPUCACHEOP_PRESENT
                                                                                |PVRSRV_MISC_INFO_RESET_PRESENT
-                                                                               |PVRSRV_MISC_INFO_FREEMEM_PRESENT))
+                                                                               |PVRSRV_MISC_INFO_FREEMEM_PRESENT
+                                                                               |PVRSRV_MISC_INFO_GET_REF_COUNT_PRESENT
+                                                                               |PVRSRV_MISC_INFO_GET_PAGE_SIZE_PRESENT
+                                                                               |PVRSRV_MISC_INFO_FORCE_SWAP_TO_SYSTEM_PRESENT))
        {
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVGetMiscInfoKM: invalid state request flags"));
                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -844,7 +1171,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
 
        SysAcquireData(&psSysData);
 
-       
+       /* return SOC Timer registers */
        if(((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_TIMER_PRESENT) != 0UL) &&
                (psSysData->pvSOCTimerRegisterKM != IMG_NULL))
        {
@@ -858,7 +1185,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                psMiscInfo->hSOCTimerRegisterOSMemHandle = IMG_NULL;
        }
 
-       
+       /* return SOC Clock Gating registers */
        if(((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_CLOCKGATE_PRESENT) != 0UL) &&
                (psSysData->pvSOCClockGateRegsBase != IMG_NULL))
        {
@@ -867,11 +1194,14 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                psMiscInfo->ui32SOCClockGateRegsSize = psSysData->ui32SOCClockGateRegsSize;
        }
 
-       
+       /* memory stats */
        if(((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_MEMSTATS_PRESENT) != 0UL) &&
                (psMiscInfo->pszMemoryStr != IMG_NULL))
        {
                RA_ARENA                        **ppArena;
+/*             BM_HEAP                         *psBMHeap;
+               BM_CONTEXT                      *psBMContext;
+               PVRSRV_DEVICE_NODE      *psDeviceNode;*/
                IMG_CHAR                        *pszStr;
                IMG_UINT32                      ui32StrLen;
                IMG_INT32                       i32Count;
@@ -881,7 +1211,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
 
                psMiscInfo->ui32StatePresent |= PVRSRV_MISC_INFO_MEMSTATS_PRESENT;
 
-               
+               /* Local backing stores */
                ppArena = &psSysData->apsLocalDevMemArena[0];
                while(*ppArena)
                {
@@ -892,12 +1222,14 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                        RA_GetStats(*ppArena,
                                                        &pszStr,
                                                        &ui32StrLen);
-                       
+                       /* advance through the array */
                        ppArena++;
                }
 
-               
-               
+               /* per device */
+/*             psDeviceNode = psSysData->psDeviceNodeList;*/
+
+               /*triple loop; devices:contexts:heaps*/
                List_PVRSRV_DEVICE_NODE_PVRSRV_ERROR_Any_va(psSysData->psDeviceNodeList,
                                                                                                        &PVRSRVGetMiscInfoKM_Device_AnyVaCb,
                                                                                                        &ui32StrLen,
@@ -905,12 +1237,12 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                                                                                                        &pszStr,
                                                                                                        PVRSRV_MISC_INFO_MEMSTATS_PRESENT);
 
-               
+               /* attach a new line and string terminate */
                i32Count = OSSNPrintf(pszStr, 100, "\n");
                UPDATE_SPACE(pszStr, i32Count, ui32StrLen);
        }
 
-       
+       /* Lean version of mem stats: only show free mem on each RA */
        if(((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_FREEMEM_PRESENT) != 0)
                && psMiscInfo->pszMemoryStr)
        {
@@ -923,7 +1255,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
   
                psMiscInfo->ui32StatePresent |= PVRSRV_MISC_INFO_FREEMEM_PRESENT;
 
-               
+               /* triple loop over devices:contexts:heaps */
                List_PVRSRV_DEVICE_NODE_PVRSRV_ERROR_Any_va(psSysData->psDeviceNodeList,
                                                                                                        &PVRSRVGetMiscInfoKM_Device_AnyVaCb,
                                                                                                        &ui32StrLen,
@@ -942,7 +1274,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                psMiscInfo->sGlobalEventObject = *psSysData->psGlobalEventObject;
        }
 
-       
+       /* DDK version and memstats not supported in same call to GetMiscInfo */
 
        if (((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_DDKVERSION_PRESENT) != 0UL)
                && ((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_MEMSTATS_PRESENT) == 0UL)
@@ -950,16 +1282,16 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
        {
                IMG_CHAR        *pszStr;
                IMG_UINT32      ui32StrLen;
-               IMG_UINT32      ui32LenStrPerNum = 12; 
+               IMG_UINT32      ui32LenStrPerNum = 12; /* string length per UI32: 10 digits + '.' + '\0' = 12 bytes */
                IMG_INT32       i32Count;
                IMG_INT i;
                psMiscInfo->ui32StatePresent |= PVRSRV_MISC_INFO_DDKVERSION_PRESENT;
 
-               
+               /* construct DDK string */
                psMiscInfo->aui32DDKVersion[0] = PVRVERSION_MAJ;
                psMiscInfo->aui32DDKVersion[1] = PVRVERSION_MIN;
-               psMiscInfo->aui32DDKVersion[2] = PVRVERSION_BRANCH;
-               psMiscInfo->aui32DDKVersion[3] = PVRVERSION_BUILD;
+               psMiscInfo->aui32DDKVersion[2] = PVRVERSION_BUILD_HI;
+               psMiscInfo->aui32DDKVersion[3] = PVRVERSION_BUILD_LO;
 
                pszStr = psMiscInfo->pszMemoryStr;
                ui32StrLen = psMiscInfo->ui32MemoryStrLen;
@@ -987,7 +1319,9 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
 
                if(psMiscInfo->sCacheOpCtl.bDeferOp)
                {
-                       
+                       /* For now, assume deferred ops are "full" cache ops,
+                        * and we don't need (or expect) a meminfo.
+                        */
                        psSysData->ePendingCacheOpType = psMiscInfo->sCacheOpCtl.eCacheOpType;
                }
                else
@@ -1018,7 +1352,6 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
 #if defined (SUPPORT_SID_INTERFACE)
                        PVR_DBG_BREAK
 #else
-                       
                        psPerProc = PVRSRVFindPerProcessData();
 
                        if(PVRSRVLookupHandle(psPerProc->psHandleBase,
@@ -1035,6 +1368,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                        if(psMiscInfo->sCacheOpCtl.eCacheOpType == PVRSRV_MISC_INFO_CPUCACHEOP_FLUSH)
                        {
                                if(!OSFlushCPUCacheRangeKM(psKernelMemInfo->sMemBlk.hOSMemHandle,
+                                                                                  0,
                                                                                   psMiscInfo->sCacheOpCtl.pvBaseVAddr,
                                                                                   psMiscInfo->sCacheOpCtl.ui32Length))
                                {
@@ -1044,6 +1378,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                        else if(psMiscInfo->sCacheOpCtl.eCacheOpType == PVRSRV_MISC_INFO_CPUCACHEOP_CLEAN)
                        {
                                if(!OSCleanCPUCacheRangeKM(psKernelMemInfo->sMemBlk.hOSMemHandle,
+                                                                                  0,
                                                                                   psMiscInfo->sCacheOpCtl.pvBaseVAddr,
                                                                                   psMiscInfo->sCacheOpCtl.ui32Length))
                                {
@@ -1053,18 +1388,71 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetMiscInfoKM(PVRSRV_MISC_INFO *psMiscInfo)
                }
        }
 
+       if((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_GET_REF_COUNT_PRESENT) != 0UL)
+       {
+#if !defined (SUPPORT_SID_INTERFACE)
+               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo;
+               PVRSRV_PER_PROCESS_DATA *psPerProc;
+#endif
+
+               psMiscInfo->ui32StatePresent |= PVRSRV_MISC_INFO_GET_REF_COUNT_PRESENT;
+
+#if defined (SUPPORT_SID_INTERFACE)
+               PVR_DBG_BREAK
+#else
+               psPerProc = PVRSRVFindPerProcessData();
+
+               if(PVRSRVLookupHandle(psPerProc->psHandleBase,
+                                                         (IMG_PVOID *)&psKernelMemInfo,
+                                                         psMiscInfo->sGetRefCountCtl.u.psKernelMemInfo,
+                                                         PVRSRV_HANDLE_TYPE_MEM_INFO) != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "PVRSRVGetMiscInfoKM: "
+                                                                       "Can't find kernel meminfo"));
+                       return PVRSRV_ERROR_INVALID_PARAMS;
+               }
+
+               psMiscInfo->sGetRefCountCtl.ui32RefCount = psKernelMemInfo->ui32RefCount;
+#endif
+       }
+
+       if ((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_GET_PAGE_SIZE_PRESENT) != 0UL)
+       {
+               psMiscInfo->ui32PageSize = HOST_PAGESIZE();
+               psMiscInfo->ui32StatePresent |= PVRSRV_MISC_INFO_GET_PAGE_SIZE_PRESENT;
+       }
+
 #if defined(PVRSRV_RESET_ON_HWTIMEOUT)
        if((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_RESET_PRESENT) != 0UL)
        {
                PVR_LOG(("User requested OS reset"));
                OSPanic();
        }
-#endif 
+#endif /* #if defined(PVRSRV_RESET_ON_HWTIMEOUT) */
+
+       if ((psMiscInfo->ui32StateRequest & PVRSRV_MISC_INFO_FORCE_SWAP_TO_SYSTEM_PRESENT) != 0UL)
+       {
+               PVRSRVSetDCState(DC_STATE_FORCE_SWAP_TO_SYSTEM);
+               psMiscInfo->ui32StatePresent |= PVRSRV_MISC_INFO_FORCE_SWAP_TO_SYSTEM_PRESENT;
+       }
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDeviceLISR
+
+ @Description
+       OS-independent Device Low-level Interrupt Service Routine
+
+ @Input psDeviceNode
+
+ @Return   IMG_BOOL : Whether any interrupts were serviced
+
+******************************************************************************/
 IMG_BOOL IMG_CALLCONV PVRSRVDeviceLISR(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        SYS_DATA                        *psSysData;
@@ -1078,7 +1466,7 @@ IMG_BOOL IMG_CALLCONV PVRSRVDeviceLISR(PVRSRV_DEVICE_NODE *psDeviceNode)
        }
        psSysData = psDeviceNode->psSysData;
 
-       
+       /* query the SOC/system to see whether this device was the source of the interrupt */
        ui32InterruptSource = SysGetInterruptSource(psSysData, psDeviceNode);
        if(ui32InterruptSource & psDeviceNode->ui32SOCInterruptBit)
        {
@@ -1112,34 +1500,50 @@ static IMG_VOID PVRSRVSystemLISR_ForEachVaCb(PVRSRV_DEVICE_NODE *psDeviceNode, v
                {
                        if((*psDeviceNode->pfnDeviceISR)(psDeviceNode->pvISRData))
                        {
-                               
+                               /* Record if serviced any interrupts. */
                                *pbStatus = IMG_TRUE;
                        }
-                       
+                       /* Combine the SOC clear bits. */
                        *pui32ClearInterrupts |= psDeviceNode->ui32SOCInterruptBit;
                }
        }
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSystemLISR
+
+ @Description
+       OS-independent System Low-level Interrupt Service Routine
+
+ @Input pvSysData
+
+ @Return   IMG_BOOL : Whether any interrupts were serviced
+
+******************************************************************************/
 IMG_BOOL IMG_CALLCONV PVRSRVSystemLISR(IMG_VOID *pvSysData)
 {
        SYS_DATA                        *psSysData = pvSysData;
        IMG_BOOL                        bStatus = IMG_FALSE;
        IMG_UINT32                      ui32InterruptSource;
        IMG_UINT32                      ui32ClearInterrupts = 0;
+/*     PVRSRV_DEVICE_NODE      *psDeviceNode;*/
+
        if(!psSysData)
        {
                PVR_DPF((PVR_DBG_ERROR, "PVRSRVSystemLISR: Invalid params\n"));
+/*             goto out; */
        }
        else
        {
-               
+               /* query SOC for source of interrupts */
                ui32InterruptSource = SysGetInterruptSource(psSysData, IMG_NULL);
 
-               
+               /* only proceed if PVR interrupts */
                if(ui32InterruptSource)
                {
-                       
+                       /* traverse the devices' ISR handlers */
                        List_PVRSRV_DEVICE_NODE_ForEach_va(psSysData->psDeviceNodeList,
                                                                                                &PVRSRVSystemLISR_ForEachVaCb,
                                                                                                &bStatus,
@@ -1148,6 +1552,7 @@ IMG_BOOL IMG_CALLCONV PVRSRVSystemLISR(IMG_VOID *pvSysData)
 
                        SysClearInterrupts(psSysData, ui32ClearInterrupts);
                }
+/*out:*/
        }
        return bStatus;
 }
@@ -1161,26 +1566,39 @@ static IMG_VOID PVRSRVMISR_ForEachCb(PVRSRV_DEVICE_NODE *psDeviceNode)
        }
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVMISR
+
+ @Input pvSysData
+
+ @Description
+       OS-independent Medium-level Interrupt Service Routine
+
+******************************************************************************/
 IMG_VOID IMG_CALLCONV PVRSRVMISR(IMG_VOID *pvSysData)
 {
        SYS_DATA                        *psSysData = pvSysData;
+/*     PVRSRV_DEVICE_NODE      *psDeviceNode; */
+
        if(!psSysData)
        {
                PVR_DPF((PVR_DBG_ERROR, "PVRSRVMISR: Invalid params\n"));
                return;
        }
 
-       
+       /* Traverse the devices' MISR handlers. */
        List_PVRSRV_DEVICE_NODE_ForEach(psSysData->psDeviceNodeList,
                                                                        &PVRSRVMISR_ForEachCb);
 
-       
+       /* Process the queues. */
        if (PVRSRVProcessQueues(IMG_FALSE) == PVRSRV_ERROR_PROCESSING_BLOCKED)
        {
                PVRSRVProcessQueues(IMG_FALSE);
        }
 
-       
+       /* signal global event object */
        if (psSysData->psGlobalEventObject)
        {
                IMG_HANDLE hOSEventKM = psSysData->psGlobalEventObject->hOSEventKM;
@@ -1192,6 +1610,18 @@ IMG_VOID IMG_CALLCONV PVRSRVMISR(IMG_VOID *pvSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVProcessConnect
+
+ @Description  Inform services that a process has connected.
+
+ @Input                ui32PID - process ID
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVProcessConnect(IMG_UINT32      ui32PID, IMG_UINT32 ui32Flags)
 {
@@ -1199,6 +1629,18 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVProcessConnect(IMG_UINT32        ui32PID, IMG_UINT32 ui
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVProcessDisconnect
+
+ @Description  Inform services that a process has disconnected.
+
+ @Input                ui32PID - process ID
+
+ @Return       IMG_VOID
+
+******************************************************************************/
 IMG_EXPORT
 IMG_VOID IMG_CALLCONV PVRSRVProcessDisconnect(IMG_UINT32       ui32PID)
 {
@@ -1206,6 +1648,20 @@ IMG_VOID IMG_CALLCONV PVRSRVProcessDisconnect(IMG_UINT32 ui32PID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVSaveRestoreLiveSegments
+
+ @Input pArena - the arena the segment was originally allocated from.
+        pbyBuffer - the system memory buffer set to null to get the size needed.
+        puiBufSize - size of system memory buffer.
+        bSave - IMG_TRUE if a save is required
+
+ @Description
+       Function to save or restore Resources Live segments
+
+******************************************************************************/
 PVRSRV_ERROR IMG_CALLCONV PVRSRVSaveRestoreLiveSegments(IMG_HANDLE hArena, IMG_PBYTE pbyBuffer,
                                                                                                                IMG_SIZE_T *puiBufSize, IMG_BOOL bSave)
 {
@@ -1222,12 +1678,12 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSaveRestoreLiveSegments(IMG_HANDLE hArena, IMG_P
        sSegDetails.sCpuPhyAddr.uiAddr = 0;
        sSegDetails.hSegment = 0;
 
-       
+       /* walk the arena segments and write live one to the  buffer */
        while (RA_GetNextLiveSegment(hArena, &sSegDetails))
        {
                if (pbyBuffer == IMG_NULL)
                {
-                       
+                       /* calc buffer required */
                        uiBytesSaved += sizeof(sSegDetails.uiSize) + sSegDetails.uiSize;
                }
                else
@@ -1239,7 +1695,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSaveRestoreLiveSegments(IMG_HANDLE hArena, IMG_P
 
                        PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVSaveRestoreLiveSegments: Base %08x size %08x", sSegDetails.sCpuPhyAddr.uiAddr, sSegDetails.uiSize));
 
-                       
+                       /* Map the device's local memory area onto the host. */
                        pvLocalMemCPUVAddr = OSMapPhysToLin(sSegDetails.sCpuPhyAddr,
                                                                        sSegDetails.uiSize,
                                                                        PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
@@ -1252,7 +1708,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSaveRestoreLiveSegments(IMG_HANDLE hArena, IMG_P
 
                        if (bSave)
                        {
-                               
+                               /* write segment size then segment data */
                                OSMemCopy(pbyBuffer, &sSegDetails.uiSize, sizeof(sSegDetails.uiSize));
                                pbyBuffer += sizeof(sSegDetails.uiSize);
 
@@ -1262,7 +1718,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSaveRestoreLiveSegments(IMG_HANDLE hArena, IMG_P
                        else
                        {
                                IMG_UINT32 uiSize;
-                               
+                               /* reag segment size and validate */
                                OSMemCopy(&uiSize, pbyBuffer, sizeof(sSegDetails.uiSize));
 
                                if (uiSize != sSegDetails.uiSize)
@@ -1297,10 +1753,28 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSaveRestoreLiveSegments(IMG_HANDLE hArena, IMG_P
 }
 
 
+/*!
+ ******************************************************************************
+
+ @Function             PVRSRVGetErrorStringKM
+
+ @Description  Returns a text string relating to the PVRSRV_ERROR enum.
+
+ @Note         case statement used rather than an indexed arrary to ensure text is
+                       synchronised with the correct enum
+
+ @Input                eError : PVRSRV_ERROR enum
+
+ @Return       const IMG_CHAR * : Text string
+
+ @Note         Must be kept in sync with servicesext.h
+
+******************************************************************************/
+
 IMG_EXPORT
 const IMG_CHAR *PVRSRVGetErrorStringKM(PVRSRV_ERROR eError)
 { 
+/* PRQA S 5087 1 */ /* include file required here */
 #include "pvrsrv_errors.h"
 }
 
@@ -1308,24 +1782,52 @@ static IMG_VOID PVRSRVCommandCompleteCallbacks_ForEachCb(PVRSRV_DEVICE_NODE *psD
 {
        if(psDeviceNode->pfnDeviceCommandComplete != IMG_NULL)
        {
-               
+               /* Call the device's callback function. */
                (*psDeviceNode->pfnDeviceCommandComplete)(psDeviceNode);
        }
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVScheduleDeviceCallbacks
+
+ @Description  Schedule all device callbacks
+
+ @Return       IMG_VOID
+
+******************************************************************************/
 IMG_VOID PVRSRVScheduleDeviceCallbacks(IMG_VOID)
 {
        SYS_DATA                                *psSysData;
+/*     PVRSRV_DEVICE_NODE              *psDeviceNode;*/
+
        SysAcquireData(&psSysData);
 
-       
+       /*for all the device, invoke the callback function*/
        List_PVRSRV_DEVICE_NODE_ForEach(psSysData->psDeviceNodeList,
                                                                        &PVRSRVCommandCompleteCallbacks_ForEachCb);
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVScheduleDevices
+
+ @Description  Schedules all Services-Managed Devices to check their pending
+                               command queues. The intention is that ScheduleDevices be called by the
+                               3rd party BC driver after it has finished writing new data to its output
+                               texture.
+
+ @Return       IMG_VOID
+
+******************************************************************************/
 IMG_EXPORT
 IMG_VOID PVRSRVScheduleDevicesKM(IMG_VOID)
 {
        PVRSRVScheduleDeviceCallbacks();
 }
 
+/*****************************************************************************
+ End of file (pvrsrv.c)
+*****************************************************************************/
index 5a1e9b4..0cfcbff 100644 (file)
@@ -1,41 +1,72 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Kernel side command queue functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
+#include "pvr_bridge_km.h"
 
 #include "lists.h"
 #include "ttrace.h"
 
+/*
+ * The number of commands of each type which can be in flight at once.
+ */
+#if defined(SUPPORT_DC_CMDCOMPLETE_WHEN_NO_LONGER_DISPLAYED)
+#define DC_NUM_COMMANDS_PER_TYPE               2
+#else
 #define DC_NUM_COMMANDS_PER_TYPE               1
-
+#endif
+
+/*
+ * List of private command processing function pointer tables and command
+ * complete tables for a device in the system.
+ * Each table is allocated when the device registers its private command
+ * processing functions.
+ */
 typedef struct _DEVICE_COMMAND_DATA_
 {
        PFN_CMD_PROC                    pfnCmdProc;
        PCOMMAND_COMPLETE_DATA  apsCmdCompleteData[DC_NUM_COMMANDS_PER_TYPE];
        IMG_UINT32                              ui32CCBOffset;
+       IMG_UINT32                              ui32MaxDstSyncCount;    /*!< Maximum number of dest syncs */
+       IMG_UINT32                              ui32MaxSrcSyncCount;    /*!< Maximum number of source syncs */
 } DEVICE_COMMAND_DATA;
 
 
@@ -43,6 +74,15 @@ typedef struct _DEVICE_COMMAND_DATA_
 
 #include "proc.h"
 
+/*****************************************************************************
+ FUNCTION      :       ProcSeqShowQueue
+
+ PURPOSE       :       Print the content of queue element  to /proc file
+                               (See env/linux/proc.c:CreateProcReadEntrySeq)
+
+ PARAMETERS    :       sfile - /proc seq_file
+                               el - Element to print
+*****************************************************************************/
 void ProcSeqShowQueue(struct seq_file *sfile,void* el)
 {
        PVRSRV_QUEUE_INFO *psQueue = (PVRSRV_QUEUE_INFO*)el;
@@ -83,16 +123,16 @@ void ProcSeqShowQueue(struct seq_file *sfile,void* el)
                                PVRSRV_SYNC_DATA *psSyncData = psCmd->psSrcSync[i].psKernelSyncInfoKM->psSyncData;
                                seq_printf(sfile, "  Sync %u: ROP/ROC: 0x%x/0x%x WOP/WOC: 0x%x/0x%x ROC-VA: 0x%x WOC-VA: 0x%x\n",
                                                                        i,
-                                                                       psCmd->psSrcSync[i].ui32ReadOpsPending,
-                                                                       psSyncData->ui32ReadOpsComplete,
+                                                                       psCmd->psSrcSync[i].ui32ReadOps2Pending,
+                                                                       psSyncData->ui32ReadOps2Complete,
                                                                        psCmd->psSrcSync[i].ui32WriteOpsPending,
                                                                        psSyncData->ui32WriteOpsComplete,
-                                                                       psCmd->psSrcSync[i].psKernelSyncInfoKM->sReadOpsCompleteDevVAddr.uiAddr,
+                                                                       psCmd->psSrcSync[i].psKernelSyncInfoKM->sReadOps2CompleteDevVAddr.uiAddr,
                                                                        psCmd->psSrcSync[i].psKernelSyncInfoKM->sWriteOpsCompleteDevVAddr.uiAddr);
                        }
                }
 
-               
+               /* taken from UPDATE_QUEUE_ROFF in queue.h */
                ui32ReadOffset += psCmd->uCmdSize;
                ui32ReadOffset &= psQueue->ui32QueueSize - 1;
                cmds++;
@@ -104,6 +144,16 @@ void ProcSeqShowQueue(struct seq_file *sfile,void* el)
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       ProcSeqOff2ElementQueue
+
+ PURPOSE       :       Transale offset to element (/proc stuff)
+
+ PARAMETERS    :       sfile - /proc seq_file
+                               off - the offset into the buffer
+
+ RETURNS    :   element to print
+*****************************************************************************/
 void* ProcSeqOff2ElementQueue(struct seq_file * sfile, loff_t off)
 {
        PVRSRV_QUEUE_INFO *psQueue = IMG_NULL;
@@ -125,19 +175,94 @@ void* ProcSeqOff2ElementQueue(struct seq_file * sfile, loff_t off)
 
        return psQueue;
 }
-#endif 
+#endif /* __linux__ && __KERNEL__ */
 
+/*!
+ * Macro to return space in given command queue
+ */
 #define GET_SPACE_IN_CMDQ(psQueue)                                                                             \
        ((((psQueue)->ui32ReadOffset - (psQueue)->ui32WriteOffset)                              \
        + ((psQueue)->ui32QueueSize - 1)) & ((psQueue)->ui32QueueSize - 1))
 
+/*!
+ * Macro to Write Offset in given command queue
+ */
 #define UPDATE_QUEUE_WOFF(psQueue, ui32Size)                                                   \
        (psQueue)->ui32WriteOffset = ((psQueue)->ui32WriteOffset + (ui32Size))  \
        & ((psQueue)->ui32QueueSize - 1);
 
+/*!
+ * Check if an ops complete value has gone past the pending value.
+ * This can happen when dummy processing multiple operations, e.g. hardware recovery.
+ */
 #define SYNCOPS_STALE(ui32OpsComplete, ui32OpsPending)                                 \
        ((ui32OpsComplete) >= (ui32OpsPending))
 
+/*!
+****************************************************************************
+ @Function     : PVRSRVGetWriteOpsPending
+
+ @Description  : Gets the next operation to wait for in a sync object
+
+ @Input        : psSyncInfo    - pointer to sync information struct
+ @Input        : bIsReadOp             - Is this a read or write op
+
+ @Return : Next op value
+*****************************************************************************/
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(PVRSRVGetWriteOpsPending)
+#endif
+static INLINE
+IMG_UINT32 PVRSRVGetWriteOpsPending(PVRSRV_KERNEL_SYNC_INFO *psSyncInfo, IMG_BOOL bIsReadOp)
+{
+       IMG_UINT32 ui32WriteOpsPending;
+
+       if(bIsReadOp)
+       {
+               ui32WriteOpsPending = psSyncInfo->psSyncData->ui32WriteOpsPending;
+       }
+       else
+       {
+               /*
+                       Note: This needs to be atomic and is provided the
+                       kernel driver is single threaded (non-rentrant)
+               */
+               ui32WriteOpsPending = psSyncInfo->psSyncData->ui32WriteOpsPending++;
+       }
+
+       return ui32WriteOpsPending;
+}
+
+/*!
+*****************************************************************************
+ @Function     : PVRSRVGetReadOpsPending
+
+ @Description  : Gets the number of pending read ops
+
+ @Input        : psSyncInfo    - pointer to sync information struct
+ @Input : bIsReadOp            - Is this a read or write op
+
+ @Return : Next op value
+*****************************************************************************/
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(PVRSRVGetReadOpsPending)
+#endif
+static INLINE
+IMG_UINT32 PVRSRVGetReadOpsPending(PVRSRV_KERNEL_SYNC_INFO *psSyncInfo, IMG_BOOL bIsReadOp)
+{
+       IMG_UINT32 ui32ReadOpsPending;
+
+       if(bIsReadOp)
+       {
+               ui32ReadOpsPending = psSyncInfo->psSyncData->ui32ReadOps2Pending++;
+       }
+       else
+       {
+               ui32ReadOpsPending = psSyncInfo->psSyncData->ui32ReadOps2Pending;
+       }
+
+       return ui32ReadOpsPending;
+}
 
 static IMG_VOID QueueDumpCmdComplete(COMMAND_COMPLETE_DATA *psCmdCompleteData,
                                                                         IMG_UINT32                             i,
@@ -151,9 +276,9 @@ static IMG_VOID QueueDumpCmdComplete(COMMAND_COMPLETE_DATA *psCmdCompleteData,
        {
                PVR_LOG(("\t%s %u: ROC DevVAddr:0x%X ROP:0x%x ROC:0x%x, WOC DevVAddr:0x%X WOP:0x%x WOC:0x%x",
                                bIsSrc ? "SRC" : "DEST", i,
-                               psSyncObject[i].psKernelSyncInfoKM->sReadOpsCompleteDevVAddr.uiAddr,
-                               psSyncObject[i].psKernelSyncInfoKM->psSyncData->ui32ReadOpsPending,
-                               psSyncObject[i].psKernelSyncInfoKM->psSyncData->ui32ReadOpsComplete,
+                               psSyncObject[i].psKernelSyncInfoKM->sReadOps2CompleteDevVAddr.uiAddr,
+                               psSyncObject[i].psKernelSyncInfoKM->psSyncData->ui32ReadOps2Pending,
+                               psSyncObject[i].psKernelSyncInfoKM->psSyncData->ui32ReadOps2Complete,
                                psSyncObject[i].psKernelSyncInfoKM->sWriteOpsCompleteDevVAddr.uiAddr,
                                psSyncObject[i].psKernelSyncInfoKM->psSyncData->ui32WriteOpsPending,
                                psSyncObject[i].psKernelSyncInfoKM->psSyncData->ui32WriteOpsComplete))
@@ -218,6 +343,10 @@ IMG_VOID QueueDumpDebugInfo(IMG_VOID)
 }
 
 
+/*****************************************************************************
+       Kernel-side functions of User->Kernel transitions
+******************************************************************************/
+
 static IMG_SIZE_T NearestPower2(IMG_SIZE_T ui32Value)
 {
        IMG_SIZE_T ui32Temp, ui32Result = 1;
@@ -236,6 +365,22 @@ static IMG_SIZE_T NearestPower2(IMG_SIZE_T ui32Value)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVCreateCommandQueueKM
+
+ @Description
+ Creates a new command queue into which render/blt commands etc can be
+ inserted.
+
+ @Input    ui32QueueSize :
+
+ @Output   ppsQueueInfo :
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateCommandQueueKM(IMG_SIZE_T ui32QueueSize,
                                                                                                         PVRSRV_QUEUE_INFO **ppsQueueInfo)
@@ -248,7 +393,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateCommandQueueKM(IMG_SIZE_T ui32QueueSize,
 
        SysAcquireData(&psSysData);
 
-       
+       /* allocate an internal queue info structure */
        eError = OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_QUEUE_INFO),
                                         (IMG_VOID **)&psQueueInfo, &hMemBlock,
@@ -263,7 +408,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateCommandQueueKM(IMG_SIZE_T ui32QueueSize,
        psQueueInfo->hMemBlock[0] = hMemBlock;
        psQueueInfo->ui32ProcessID = OSGetCurrentProcessIDKM();
 
-       
+       /* allocate the command queue buffer - allow for overrun */
        eError = OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                         ui32Power2QueueSize + PVRSRV_MAX_CMD_SIZE,
                                         &psQueueInfo->pvLinQueueKM, &hMemBlock,
@@ -277,13 +422,13 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateCommandQueueKM(IMG_SIZE_T ui32QueueSize,
        psQueueInfo->hMemBlock[1] = hMemBlock;
        psQueueInfo->pvLinQueueUM = psQueueInfo->pvLinQueueKM;
 
-       
+       /* Sanity check: Should be zeroed by OSMemSet */
        PVR_ASSERT(psQueueInfo->ui32ReadOffset == 0);
        PVR_ASSERT(psQueueInfo->ui32WriteOffset == 0);
 
        psQueueInfo->ui32QueueSize = ui32Power2QueueSize;
 
-       
+       /* if this is the first q, create a lock resource for the q list */
        if (psSysData->psQueueList == IMG_NULL)
        {
                eError = OSCreateResource(&psSysData->sQProcessResource);
@@ -293,7 +438,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVCreateCommandQueueKM(IMG_SIZE_T ui32QueueSize,
                }
        }
 
-       
+       /* Ensure we don't corrupt queue list, by blocking access */
        eError = OSLockResource(&psSysData->sQProcessResource,
                                                        KERNEL_ID);
        if (eError != PVRSRV_OK)
@@ -331,13 +476,25 @@ ErrorExit:
                                        sizeof(PVRSRV_QUEUE_INFO),
                                        psQueueInfo,
                                        psQueueInfo->hMemBlock[0]);
-               
+               /*not nulling pointer, out of scope*/
        }
 
        return eError;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDestroyCommandQueueKM
+
+ @Description  Destroys a command queue
+
+ @Input                psQueueInfo :
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyCommandQueueKM(PVRSRV_QUEUE_INFO *psQueueInfo)
 {
@@ -350,7 +507,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyCommandQueueKM(PVRSRV_QUEUE_INFO *psQueue
 
        psQueue = psSysData->psQueueList;
 
-        
+       /* PRQA S 3415,4109 1 */ /* macro format critical - leave alone */
        LOOP_UNTIL_TIMEOUT(MAX_HW_TIME_US)
        {
                if(psQueueInfo->ui32ReadOffset == psQueueInfo->ui32WriteOffset)
@@ -363,13 +520,14 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyCommandQueueKM(PVRSRV_QUEUE_INFO *psQueue
 
        if (bTimeout)
        {
-               
+               /* The command queue could not be flushed within the timeout period.
+               Allow the queue to be destroyed before returning the error code. */
                PVR_DPF((PVR_DBG_ERROR,"PVRSRVDestroyCommandQueueKM : Failed to empty queue"));
                eError = PVRSRV_ERROR_CANNOT_FLUSH_QUEUE;
                goto ErrorExit;
        }
 
-       
+       /* Ensure we don't corrupt queue list, by blocking access */
        eError = OSLockResource(&psSysData->sQProcessResource,
                                                                KERNEL_ID);
        if (eError != PVRSRV_OK)
@@ -390,8 +548,8 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyCommandQueueKM(PVRSRV_QUEUE_INFO *psQueue
                                        sizeof(PVRSRV_QUEUE_INFO),
                                        psQueueInfo,
                                        psQueueInfo->hMemBlock[0]);
-                
-               psQueueInfo = IMG_NULL; 
+               /* PRQA S 3199 1 */ /* see note */
+               psQueueInfo = IMG_NULL; /*it's a copy on stack, but null it because the function doesn't end right here*/
        }
        else
        {
@@ -410,8 +568,8 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyCommandQueueKM(PVRSRV_QUEUE_INFO *psQueue
                                                        sizeof(PVRSRV_QUEUE_INFO),
                                                        psQueueInfo,
                                                        psQueueInfo->hMemBlock[0]);
-                                
-                               psQueueInfo = IMG_NULL; 
+                               /* PRQA S 3199 1 */ /* see note */
+                               psQueueInfo = IMG_NULL; /*it's a copy on stack, but null it because the function doesn't end right here*/
                                break;
                        }
                        psQueue = psQueue->psNextKM;
@@ -429,14 +587,14 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDestroyCommandQueueKM(PVRSRV_QUEUE_INFO *psQueue
                }
        }
 
-       
+       /*  unlock the Q list lock resource */
        eError = OSUnlockResource(&psSysData->sQProcessResource, KERNEL_ID);
        if (eError != PVRSRV_OK)
        {
                goto ErrorExit;
        }
 
-       
+       /*  if the Q list is now empty, destroy the Q list lock resource */
        if (psSysData->psQueueList == IMG_NULL)
        {
                eError = OSDestroyResource(&psSysData->sQProcessResource);
@@ -452,6 +610,20 @@ ErrorExit:
 }
 
 
+/*!
+*****************************************************************************
+
+ @Function     : PVRSRVGetQueueSpaceKM
+
+ @Description  : Waits for queue access rights and checks for available space in
+                         queue for task param structure
+
+ @Input        : psQueue               - pointer to queue information struct
+ @Input : ui32ParamSize - size of task data structure
+ @Output : ppvSpace
+
+ @Return       : PVRSRV_ERROR
+*****************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetQueueSpaceKM(PVRSRV_QUEUE_INFO *psQueue,
                                                                                                IMG_SIZE_T ui32ParamSize,
@@ -459,7 +631,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetQueueSpaceKM(PVRSRV_QUEUE_INFO *psQueue,
 {
        IMG_BOOL bTimeout = IMG_TRUE;
 
-       
+       /*      round to 4byte units */
        ui32ParamSize =  (ui32ParamSize+3) & 0xFFFFFFFC;
 
        if (ui32ParamSize > PVRSRV_MAX_CMD_SIZE)
@@ -468,7 +640,7 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetQueueSpaceKM(PVRSRV_QUEUE_INFO *psQueue,
                return PVRSRV_ERROR_CMD_TOO_BIG;
        }
 
-        
+       /* PRQA S 3415,4109 1 */ /* macro format critical - leave alone */
        LOOP_UNTIL_TIMEOUT(MAX_HW_TIME_US)
        {
                if (GET_SPACE_IN_CMDQ(psQueue) > ui32ParamSize)
@@ -494,6 +666,26 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVGetQueueSpaceKM(PVRSRV_QUEUE_INFO *psQueue,
 }
 
 
+/*!
+*****************************************************************************
+ @Function     PVRSRVInsertCommandKM
+
+ @Description :
+                       command insertion utility
+                        - waits for space in the queue for a new command
+                        - fills in generic command information
+                        - returns a pointer to the caller who's expected to then fill
+                               in the private data.
+                       The caller should follow PVRSRVInsertCommand with PVRSRVSubmitCommand
+                       which will update the queue's write offset so the command can be
+                       executed.
+
+ @Input                psQueue : pointer to queue information struct
+
+ @Output       ppvCmdData : holds pointer to space in queue for private cmd data
+
+ @Return       PVRSRV_ERROR
+*****************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVInsertCommandKM(PVRSRV_QUEUE_INFO      *psQueue,
                                                                                                PVRSRV_COMMAND          **ppsCommand,
@@ -503,22 +695,37 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInsertCommandKM(PVRSRV_QUEUE_INFO *psQueue,
                                                                                                PVRSRV_KERNEL_SYNC_INFO *apsDstSync[],
                                                                                                IMG_UINT32                      ui32SrcSyncCount,
                                                                                                PVRSRV_KERNEL_SYNC_INFO *apsSrcSync[],
-                                                                                               IMG_SIZE_T                      ui32DataByteSize )
+                                                                                               IMG_SIZE_T                      ui32DataByteSize,
+                                                                                               PFN_QUEUE_COMMAND_COMPLETE pfnCommandComplete,
+                                                                                               IMG_HANDLE                      hCallbackData)
 {
        PVRSRV_ERROR    eError;
        PVRSRV_COMMAND  *psCommand;
        IMG_SIZE_T              ui32CommandSize;
        IMG_UINT32              i;
+       SYS_DATA *psSysData;
+       DEVICE_COMMAND_DATA *psDeviceCommandData;
 
-       
+       /* Check that we've got enough space in our command complete data for this command */
+       SysAcquireData(&psSysData);
+       psDeviceCommandData = psSysData->apsDeviceCommandData[ui32DevIndex];
+
+       if ((psDeviceCommandData[CommandType].ui32MaxDstSyncCount < ui32DstSyncCount) ||
+          (psDeviceCommandData[CommandType].ui32MaxSrcSyncCount < ui32SrcSyncCount))
+       {
+               PVR_DPF((PVR_DBG_ERROR, "PVRSRVInsertCommandKM: Too many syncs"));
+               return PVRSRV_ERROR_INVALID_PARAMS;
+       }
+
+       /* Round up to nearest 32 bit size so pointer arithmetic works */
        ui32DataByteSize = (ui32DataByteSize + 3UL) & ~3UL;
 
-       
+       /*  calc. command size */
        ui32CommandSize = sizeof(PVRSRV_COMMAND)
                                        + ((ui32DstSyncCount + ui32SrcSyncCount) * sizeof(PVRSRV_SYNC_OBJECT))
                                        + ui32DataByteSize;
 
-       
+       /* wait for space in queue */
        eError = PVRSRVGetQueueSpaceKM (psQueue, ui32CommandSize, (IMG_VOID**)&psCommand);
        if(eError != PVRSRV_OK)
        {
@@ -527,14 +734,14 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInsertCommandKM(PVRSRV_QUEUE_INFO *psQueue,
 
        psCommand->ui32ProcessID        = OSGetCurrentProcessIDKM();
 
-       
-       psCommand->uCmdSize             = ui32CommandSize; 
+       /* setup the command */
+       psCommand->uCmdSize             = ui32CommandSize; /* this may change if cmd shrinks */
        psCommand->ui32DevIndex         = ui32DevIndex;
        psCommand->CommandType          = CommandType;
        psCommand->ui32DstSyncCount     = ui32DstSyncCount;
        psCommand->ui32SrcSyncCount     = ui32SrcSyncCount;
-       
-       
+       /* override QAC warning about stricter pointers */
+       /* PRQA S 3305 END_PTR_ASSIGNMENTS */
        psCommand->psDstSync            = (PVRSRV_SYNC_OBJECT*)(((IMG_UINTPTR_T)psCommand) + sizeof(PVRSRV_COMMAND));
 
 
@@ -543,13 +750,18 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInsertCommandKM(PVRSRV_QUEUE_INFO *psQueue,
 
        psCommand->pvData                       = (PVRSRV_SYNC_OBJECT*)(((IMG_UINTPTR_T)psCommand->psSrcSync)
                                                                + (ui32SrcSyncCount * sizeof(PVRSRV_SYNC_OBJECT)));
-       psCommand->uDataSize            = ui32DataByteSize;
+/* PRQA L:END_PTR_ASSIGNMENTS */
+
+       psCommand->uDataSize            = ui32DataByteSize;/* this may change if cmd shrinks */
+
+       psCommand->pfnCommandComplete = pfnCommandComplete;
+       psCommand->hCallbackData = hCallbackData;
 
        PVR_TTRACE(PVRSRV_TRACE_GROUP_QUEUE, PVRSRV_TRACE_CLASS_CMD_START, QUEUE_TOKEN_INSERTKM);
        PVR_TTRACE_UI32(PVRSRV_TRACE_GROUP_QUEUE, PVRSRV_TRACE_CLASS_NONE,
                        QUEUE_TOKEN_COMMAND_TYPE, CommandType);
 
-       
+       /* setup dst sync objects and their sync dependencies */
        for (i=0; i<ui32DstSyncCount; i++)
        {
                PVR_TTRACE_SYNC_OBJECT(PVRSRV_TRACE_GROUP_QUEUE, QUEUE_TOKEN_DST_SYNC,
@@ -557,16 +769,18 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInsertCommandKM(PVRSRV_QUEUE_INFO *psQueue,
 
                psCommand->psDstSync[i].psKernelSyncInfoKM = apsDstSync[i];
                psCommand->psDstSync[i].ui32WriteOpsPending = PVRSRVGetWriteOpsPending(apsDstSync[i], IMG_FALSE);
-               psCommand->psDstSync[i].ui32ReadOpsPending = PVRSRVGetReadOpsPending(apsDstSync[i], IMG_FALSE);
+               psCommand->psDstSync[i].ui32ReadOps2Pending = PVRSRVGetReadOpsPending(apsDstSync[i], IMG_FALSE);
+
+               PVRSRVKernelSyncInfoIncRef(apsDstSync[i], IMG_NULL);
 
                PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVInsertCommandKM: Dst %u RO-VA:0x%x WO-VA:0x%x ROP:0x%x WOP:0x%x",
-                               i, psCommand->psDstSync[i].psKernelSyncInfoKM->sReadOpsCompleteDevVAddr.uiAddr,
+                               i, psCommand->psDstSync[i].psKernelSyncInfoKM->sReadOps2CompleteDevVAddr.uiAddr,
                                psCommand->psDstSync[i].psKernelSyncInfoKM->sWriteOpsCompleteDevVAddr.uiAddr,
-                               psCommand->psDstSync[i].ui32ReadOpsPending,
+                               psCommand->psDstSync[i].ui32ReadOps2Pending,
                                psCommand->psDstSync[i].ui32WriteOpsPending));
        }
 
-       
+       /* setup src sync objects and their sync dependencies */
        for (i=0; i<ui32SrcSyncCount; i++)
        {
                PVR_TTRACE_SYNC_OBJECT(PVRSRV_TRACE_GROUP_QUEUE, QUEUE_TOKEN_DST_SYNC,
@@ -574,30 +788,44 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInsertCommandKM(PVRSRV_QUEUE_INFO *psQueue,
 
                psCommand->psSrcSync[i].psKernelSyncInfoKM = apsSrcSync[i];
                psCommand->psSrcSync[i].ui32WriteOpsPending = PVRSRVGetWriteOpsPending(apsSrcSync[i], IMG_TRUE);
-               psCommand->psSrcSync[i].ui32ReadOpsPending = PVRSRVGetReadOpsPending(apsSrcSync[i], IMG_TRUE);
+               psCommand->psSrcSync[i].ui32ReadOps2Pending = PVRSRVGetReadOpsPending(apsSrcSync[i], IMG_TRUE);
+
+               PVRSRVKernelSyncInfoIncRef(apsSrcSync[i], IMG_NULL);
 
                PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVInsertCommandKM: Src %u RO-VA:0x%x WO-VA:0x%x ROP:0x%x WOP:0x%x",
-                               i, psCommand->psSrcSync[i].psKernelSyncInfoKM->sReadOpsCompleteDevVAddr.uiAddr,
+                               i, psCommand->psSrcSync[i].psKernelSyncInfoKM->sReadOps2CompleteDevVAddr.uiAddr,
                                psCommand->psSrcSync[i].psKernelSyncInfoKM->sWriteOpsCompleteDevVAddr.uiAddr,
-                               psCommand->psSrcSync[i].ui32ReadOpsPending,
+                               psCommand->psSrcSync[i].ui32ReadOps2Pending,
                                psCommand->psSrcSync[i].ui32WriteOpsPending));
        }
        PVR_TTRACE(PVRSRV_TRACE_GROUP_QUEUE, PVRSRV_TRACE_CLASS_CMD_END, QUEUE_TOKEN_INSERTKM);
 
-       
+       /* return pointer to caller to fill out private data */
        *ppsCommand = psCommand;
 
        return PVRSRV_OK;
 }
 
 
+/*!
+*******************************************************************************
+ @Function     : PVRSRVSubmitCommandKM
+
+ @Description :
+                        updates the queue's write offset so the command can be executed.
+
+ @Input        : psQueue               -       queue command is in
+ @Input        : psCommand
+
+ @Return : PVRSRV_ERROR
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVSubmitCommandKM(PVRSRV_QUEUE_INFO *psQueue,
                                                                                                PVRSRV_COMMAND *psCommand)
 {
-       
-       
-       
+       /* override QAC warnings about stricter pointers */
+       /* PRQA S 3305 END_PTR_ASSIGNMENTS2 */
+       /* patch pointers in the command to be kernel pointers */
        if (psCommand->ui32DstSyncCount > 0)
        {
                psCommand->psDstSync = (PVRSRV_SYNC_OBJECT*)(((IMG_UINTPTR_T)psQueue->pvLinQueueKM)
@@ -616,14 +844,84 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVSubmitCommandKM(PVRSRV_QUEUE_INFO *psQueue,
                                                                        + (psCommand->ui32DstSyncCount * sizeof(PVRSRV_SYNC_OBJECT))
                                                                        + (psCommand->ui32SrcSyncCount * sizeof(PVRSRV_SYNC_OBJECT)));
 
-       
+/* PRQA L:END_PTR_ASSIGNMENTS2 */
+
+       /* update write offset before releasing access lock */
        UPDATE_QUEUE_WOFF(psQueue, psCommand->uCmdSize);
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
 
+ @Function     CheckIfSyncIsQueued
 
+ @Description  Check if the specificed sync object is already queued and
+                can safely be given to the display controller.
+                This check is required as a 3rd party displayclass device can
+                have several flips "in flight" and we need to ensure that we
+                keep their pipeline full and don't deadlock waiting for them
+                to complete an operation on a surface.
+
+ @Input                psSysData : system data
+ @Input                psCmdData : COMMAND_COMPLETE_DATA structure
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
+static
+PVRSRV_ERROR CheckIfSyncIsQueued(PVRSRV_SYNC_OBJECT *psSync, COMMAND_COMPLETE_DATA *psCmdData)
+{
+       IMG_UINT32 k;
+       if (psCmdData->bInUse)
+       {
+               for (k=0;k<psCmdData->ui32SrcSyncCount;k++)
+               {
+                       if (psSync->psKernelSyncInfoKM == psCmdData->psSrcSync[k].psKernelSyncInfoKM)
+                       {
+                               PVRSRV_SYNC_DATA *psSyncData = psSync->psKernelSyncInfoKM->psSyncData;
+                               IMG_UINT32 ui32WriteOpsComplete = psSyncData->ui32WriteOpsComplete;
+
+                               /*
+                                       We still need to ensure that we don't we don't give a command
+                                       to the display controller if writes are outstanding on it
+                               */
+                               if (ui32WriteOpsComplete == psSync->ui32WriteOpsPending)
+                               {
+                                       return PVRSRV_OK;
+                               }
+                               else
+                               {
+                                       if (SYNCOPS_STALE(ui32WriteOpsComplete, psSync->ui32WriteOpsPending))
+                                       {
+                                               PVR_DPF((PVR_DBG_WARNING,
+                                                               "CheckIfSyncIsQueued: Stale syncops psSyncData:0x%x ui32WriteOpsComplete:0x%x ui32WriteOpsPending:0x%x",
+                                                               (IMG_UINTPTR_T)psSyncData, ui32WriteOpsComplete, psSync->ui32WriteOpsPending));
+                                               return PVRSRV_OK;
+                                       }
+                               }
+                       }
+               }
+       }
+       return PVRSRV_ERROR_FAILED_DEPENDENCIES;
+}
+
+/*!
+******************************************************************************
+
+ @Function     PVRSRVProcessCommand
+
+ @Description  Tries to process a command
+
+ @Input                psSysData : system data
+ @Input                psCommand : PVRSRV_COMMAND structure
+ @Input                bFlush : Check for stale dependencies (only used for HW recovery)
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 static
 PVRSRV_ERROR PVRSRVProcessCommand(SYS_DATA                     *psSysData,
                                                                  PVRSRV_COMMAND        *psCommand,
@@ -639,7 +937,7 @@ PVRSRV_ERROR PVRSRVProcessCommand(SYS_DATA                  *psSysData,
        DEVICE_COMMAND_DATA             *psDeviceCommandData;
        IMG_UINT32                              ui32CCBOffset;
 
-       
+       /* satisfy sync dependencies on the DST(s) */
        psWalkerObj = psCommand->psDstSync;
        psEndObj = psWalkerObj + psCommand->ui32DstSyncCount;
        while (psWalkerObj < psEndObj)
@@ -647,14 +945,14 @@ PVRSRV_ERROR PVRSRVProcessCommand(SYS_DATA                        *psSysData,
                PVRSRV_SYNC_DATA *psSyncData = psWalkerObj->psKernelSyncInfoKM->psSyncData;
 
                ui32WriteOpsComplete = psSyncData->ui32WriteOpsComplete;
-               ui32ReadOpsComplete = psSyncData->ui32ReadOpsComplete;
-               
+               ui32ReadOpsComplete = psSyncData->ui32ReadOps2Complete;
+               /* fail if reads or writes are not up to date */
                if ((ui32WriteOpsComplete != psWalkerObj->ui32WriteOpsPending)
-               ||      (ui32ReadOpsComplete != psWalkerObj->ui32ReadOpsPending))
+               ||      (ui32ReadOpsComplete != psWalkerObj->ui32ReadOps2Pending))
                {
                        if (!bFlush ||
                                !SYNCOPS_STALE(ui32WriteOpsComplete, psWalkerObj->ui32WriteOpsPending) ||
-                               !SYNCOPS_STALE(ui32ReadOpsComplete, psWalkerObj->ui32ReadOpsPending))
+                               !SYNCOPS_STALE(ui32ReadOpsComplete, psWalkerObj->ui32ReadOps2Pending))
                        {
                                return PVRSRV_ERROR_FAILED_DEPENDENCIES;
                        }
@@ -663,22 +961,22 @@ PVRSRV_ERROR PVRSRVProcessCommand(SYS_DATA                        *psSysData,
                psWalkerObj++;
        }
 
-       
+       /* satisfy sync dependencies on the SRC(s) */
        psWalkerObj = psCommand->psSrcSync;
        psEndObj = psWalkerObj + psCommand->ui32SrcSyncCount;
        while (psWalkerObj < psEndObj)
        {
                PVRSRV_SYNC_DATA *psSyncData = psWalkerObj->psKernelSyncInfoKM->psSyncData;
 
-               ui32ReadOpsComplete = psSyncData->ui32ReadOpsComplete;
+               ui32ReadOpsComplete = psSyncData->ui32ReadOps2Complete;
                ui32WriteOpsComplete = psSyncData->ui32WriteOpsComplete;
-               
+               /* fail if writes are not up to date */
                if ((ui32WriteOpsComplete != psWalkerObj->ui32WriteOpsPending)
-               || (ui32ReadOpsComplete != psWalkerObj->ui32ReadOpsPending))
+               || (ui32ReadOpsComplete != psWalkerObj->ui32ReadOps2Pending))
                {
                        if (!bFlush &&
                                SYNCOPS_STALE(ui32WriteOpsComplete, psWalkerObj->ui32WriteOpsPending) &&
-                               SYNCOPS_STALE(ui32ReadOpsComplete, psWalkerObj->ui32ReadOpsPending))
+                               SYNCOPS_STALE(ui32ReadOpsComplete, psWalkerObj->ui32ReadOps2Pending))
                        {
                                PVR_DPF((PVR_DBG_WARNING,
                                                "PVRSRVProcessCommand: Stale syncops psSyncData:0x%x ui32WriteOpsComplete:0x%x ui32WriteOpsPending:0x%x",
@@ -687,15 +985,30 @@ PVRSRV_ERROR PVRSRVProcessCommand(SYS_DATA                        *psSysData,
 
                        if (!bFlush ||
                                !SYNCOPS_STALE(ui32WriteOpsComplete, psWalkerObj->ui32WriteOpsPending) ||
-                               !SYNCOPS_STALE(ui32ReadOpsComplete, psWalkerObj->ui32ReadOpsPending))
+                               !SYNCOPS_STALE(ui32ReadOpsComplete, psWalkerObj->ui32ReadOps2Pending))
                        {
-                               return PVRSRV_ERROR_FAILED_DEPENDENCIES;
+                               IMG_UINT32 j;
+                               PVRSRV_ERROR eError;
+                               IMG_BOOL bFound = IMG_FALSE;
+
+                               psDeviceCommandData = psSysData->apsDeviceCommandData[psCommand->ui32DevIndex];
+                               for (j=0;j<DC_NUM_COMMANDS_PER_TYPE;j++)
+                               {
+                                       eError = CheckIfSyncIsQueued(psWalkerObj, psDeviceCommandData[psCommand->CommandType].apsCmdCompleteData[j]);
+
+                                       if (eError == PVRSRV_OK)
+                                       {
+                                               bFound = IMG_TRUE;
+                                       }
+                               }
+                               if (!bFound)
+                                       return PVRSRV_ERROR_FAILED_DEPENDENCIES;
                        }
                }
                psWalkerObj++;
        }
 
-       
+       /* validate device type */
        if (psCommand->ui32DevIndex >= SYS_DEVICE_COUNT)
        {
                PVR_DPF((PVR_DBG_ERROR,
@@ -704,70 +1017,74 @@ PVRSRV_ERROR PVRSRVProcessCommand(SYS_DATA                       *psSysData,
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* fish out the appropriate storage structure for the duration of the command */
        psDeviceCommandData = psSysData->apsDeviceCommandData[psCommand->ui32DevIndex];
        ui32CCBOffset = psDeviceCommandData[psCommand->CommandType].ui32CCBOffset;
        psCmdCompleteData = psDeviceCommandData[psCommand->CommandType].apsCmdCompleteData[ui32CCBOffset];
        if (psCmdCompleteData->bInUse)
        {
-               
+               /* can use this to protect against concurrent execution of same command */
                return PVRSRV_ERROR_FAILED_DEPENDENCIES;
        }
 
-       
+       /* mark the structure as in use */
        psCmdCompleteData->bInUse = IMG_TRUE;
 
-       
+       /* copy src updates over */
        psCmdCompleteData->ui32DstSyncCount = psCommand->ui32DstSyncCount;
        for (i=0; i<psCommand->ui32DstSyncCount; i++)
        {
                psCmdCompleteData->psDstSync[i] = psCommand->psDstSync[i];
 
                PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVProcessCommand: Dst %u RO-VA:0x%x WO-VA:0x%x ROP:0x%x WOP:0x%x (CCB:%u)",
-                               i, psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM->sReadOpsCompleteDevVAddr.uiAddr,
+                               i, psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM->sReadOps2CompleteDevVAddr.uiAddr,
                                psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM->sWriteOpsCompleteDevVAddr.uiAddr,
-                               psCmdCompleteData->psDstSync[i].ui32ReadOpsPending,
+                               psCmdCompleteData->psDstSync[i].ui32ReadOps2Pending,
                                psCmdCompleteData->psDstSync[i].ui32WriteOpsPending,
                                ui32CCBOffset));
        }
 
+       psCmdCompleteData->pfnCommandComplete = psCommand->pfnCommandComplete;
+       psCmdCompleteData->hCallbackData = psCommand->hCallbackData;
 
-       
+       /* copy dst updates over */
        psCmdCompleteData->ui32SrcSyncCount = psCommand->ui32SrcSyncCount;
        for (i=0; i<psCommand->ui32SrcSyncCount; i++)
        {
                psCmdCompleteData->psSrcSync[i] = psCommand->psSrcSync[i];
 
                PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVProcessCommand: Src %u RO-VA:0x%x WO-VA:0x%x ROP:0x%x WOP:0x%x (CCB:%u)",
-                               i, psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM->sReadOpsCompleteDevVAddr.uiAddr,
+                               i, psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM->sReadOps2CompleteDevVAddr.uiAddr,
                                psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM->sWriteOpsCompleteDevVAddr.uiAddr,
-                               psCmdCompleteData->psSrcSync[i].ui32ReadOpsPending,
+                               psCmdCompleteData->psSrcSync[i].ui32ReadOps2Pending,
                                psCmdCompleteData->psSrcSync[i].ui32WriteOpsPending,
                                ui32CCBOffset));
        }
 
-       
-
-
-
-
-
-
-
-
-
+       /*
+               call the cmd specific handler:
+               it should:
+                - check the cmd specific dependencies
+                - setup private cmd complete structure
+                - execute cmd on HW
+                - store psCmdCompleteData `cookie' and later pass as
+                       argument to Generic Command Complete Callback
+
+               n.b. ui32DataSize (packet size) is useful for packet validation
+       */
        if (psDeviceCommandData[psCommand->CommandType].pfnCmdProc((IMG_HANDLE)psCmdCompleteData,
                                                                                                                           (IMG_UINT32)psCommand->uDataSize,
                                                                                                                           psCommand->pvData) == IMG_FALSE)
        {
-               
-
-
+               /*
+                       clean-up:
+                       free cmd complete structure
+               */
                psCmdCompleteData->bInUse = IMG_FALSE;
                eError = PVRSRV_ERROR_CMD_NOT_PROCESSED;
        }
        
-       
+       /* Increment the CCB offset */
        psDeviceCommandData[psCommand->CommandType].ui32CCBOffset = (ui32CCBOffset + 1) % DC_NUM_COMMANDS_PER_TYPE;
 
        return eError;
@@ -783,19 +1100,37 @@ static IMG_VOID PVRSRVProcessQueues_ForEachCb(PVRSRV_DEVICE_NODE *psDeviceNode)
        }
 }
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVProcessQueues
+
+ @Description  Tries to process a command from each Q
+
+ @input ui32CallerID - used to distinguish between async ISR/DPC type calls
+                                               the synchronous services driver
+ @input        bFlush - flush commands with stale dependencies (only used for HW recovery)
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
+
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVProcessQueues(IMG_BOOL      bFlush)
 {
        PVRSRV_QUEUE_INFO       *psQueue;
        SYS_DATA                        *psSysData;
        PVRSRV_COMMAND          *psCommand;
-       SysAcquireData(&psSysData);
+/*     PVRSRV_DEVICE_NODE      *psDeviceNode;*/
 
-       
+       SysAcquireData(&psSysData);
 
+       /* Ensure we don't corrupt queue list, by blocking access. This is required for OSs where
+           multiple ISR threads may exist simultaneously (eg WinXP DPC routines)
+       */
        while (OSLockResource(&psSysData->sQProcessResource, ISR_ID) != PVRSRV_OK)
        {
-               OSSleepms(1);
+               OSWaitus(1);
        };
        
        psQueue = psSysData->psQueueList;
@@ -818,7 +1153,7 @@ PVRSRV_ERROR PVRSRVProcessQueues(IMG_BOOL  bFlush)
 
                        if (PVRSRVProcessCommand(psSysData, psCommand, bFlush) == PVRSRV_OK)
                        {
-                               
+                               /* processed cmd so update queue */
                                UPDATE_QUEUE_ROFF(psQueue, psCommand->uCmdSize)
                                continue;
                        }
@@ -833,7 +1168,7 @@ PVRSRV_ERROR PVRSRVProcessQueues(IMG_BOOL  bFlush)
                PVRSRVSetDCState(DC_STATE_NO_FLUSH_COMMANDS);
        }
 
-       
+       /* Re-process command complete handlers if necessary. */
        List_PVRSRV_DEVICE_NODE_ForEach(psSysData->psDeviceNodeList,
                                                                        &PVRSRVProcessQueues_ForEachCb);
 
@@ -843,6 +1178,19 @@ PVRSRV_ERROR PVRSRVProcessQueues(IMG_BOOL bFlush)
 }
 
 #if defined(SUPPORT_CUSTOM_SWAP_OPERATIONS)
+/*!
+******************************************************************************
+
+ @Function     PVRSRVCommandCompleteKM
+
+ @Description  Updates non-private command complete sync objects
+
+ @Input                hCmdCookie : command cookie
+ @Input                bScheduleMISR : obsolete parameter
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_INTERNAL
 IMG_VOID PVRSRVFreeCommandCompletePacketKM(IMG_HANDLE  hCmdCookie,
                                                                                   IMG_BOOL             bScheduleMISR)
@@ -850,23 +1198,36 @@ IMG_VOID PVRSRVFreeCommandCompletePacketKM(IMG_HANDLE    hCmdCookie,
        COMMAND_COMPLETE_DATA   *psCmdCompleteData = (COMMAND_COMPLETE_DATA *)hCmdCookie;
        SYS_DATA                                *psSysData;
 
+       PVR_UNREFERENCED_PARAMETER(bScheduleMISR);
+
        SysAcquireData(&psSysData);
 
-       
+       /* free command complete storage */
        psCmdCompleteData->bInUse = IMG_FALSE;
 
-       
+       /* FIXME: This may cause unrelated devices to be woken up. */
        PVRSRVScheduleDeviceCallbacks();
 
-       if(bScheduleMISR)
-       {
-               OSScheduleMISR(psSysData);
-       }
+       /* the MISR is always scheduled, regardless of bScheduleMISR */
+       OSScheduleMISR(psSysData);
 }
 
-#endif 
+#endif /* (SUPPORT_CUSTOM_SWAP_OPERATIONS) */
+
+
+/*!
+******************************************************************************
+
+ @Function     PVRSRVCommandCompleteKM
+
+ @Description  Updates non-private command complete sync objects
 
+ @Input                hCmdCookie : command cookie
+ @Input                bScheduleMISR : boolean to schedule MISR
 
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 IMG_VOID PVRSRVCommandCompleteKM(IMG_HANDLE    hCmdCookie,
                                                                 IMG_BOOL       bScheduleMISR)
@@ -880,45 +1241,54 @@ IMG_VOID PVRSRVCommandCompleteKM(IMG_HANDLE      hCmdCookie,
        PVR_TTRACE(PVRSRV_TRACE_GROUP_QUEUE, PVRSRV_TRACE_CLASS_CMD_COMP_START,
                        QUEUE_TOKEN_COMMAND_COMPLETE);
 
-       
+       /* update DST(s) syncs */
        for (i=0; i<psCmdCompleteData->ui32DstSyncCount; i++)
        {
                psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM->psSyncData->ui32WriteOpsComplete++;
 
+               PVRSRVKernelSyncInfoDecRef(psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM, IMG_NULL);
+
                PVR_TTRACE_SYNC_OBJECT(PVRSRV_TRACE_GROUP_QUEUE, QUEUE_TOKEN_UPDATE_DST,
                                          psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM,
                                          PVRSRV_SYNCOP_COMPLETE);
 
                PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVCommandCompleteKM: Dst %u RO-VA:0x%x WO-VA:0x%x ROP:0x%x WOP:0x%x",
-                               i, psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM->sReadOpsCompleteDevVAddr.uiAddr,
+                               i, psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM->sReadOps2CompleteDevVAddr.uiAddr,
                                psCmdCompleteData->psDstSync[i].psKernelSyncInfoKM->sWriteOpsCompleteDevVAddr.uiAddr,
-                               psCmdCompleteData->psDstSync[i].ui32ReadOpsPending,
+                               psCmdCompleteData->psDstSync[i].ui32ReadOps2Pending,
                                psCmdCompleteData->psDstSync[i].ui32WriteOpsPending));
        }
 
-       
+       /* update SRC(s) syncs */
        for (i=0; i<psCmdCompleteData->ui32SrcSyncCount; i++)
        {
-               psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM->psSyncData->ui32ReadOpsComplete++;
+               psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM->psSyncData->ui32ReadOps2Complete++;
+
+               PVRSRVKernelSyncInfoDecRef(psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM, IMG_NULL);
 
                PVR_TTRACE_SYNC_OBJECT(PVRSRV_TRACE_GROUP_QUEUE, QUEUE_TOKEN_UPDATE_SRC,
                                          psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM,
                                          PVRSRV_SYNCOP_COMPLETE);
 
                PVR_DPF((PVR_DBG_MESSAGE, "PVRSRVCommandCompleteKM: Src %u RO-VA:0x%x WO-VA:0x%x ROP:0x%x WOP:0x%x",
-                               i, psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM->sReadOpsCompleteDevVAddr.uiAddr,
+                               i, psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM->sReadOps2CompleteDevVAddr.uiAddr,
                                psCmdCompleteData->psSrcSync[i].psKernelSyncInfoKM->sWriteOpsCompleteDevVAddr.uiAddr,
-                               psCmdCompleteData->psSrcSync[i].ui32ReadOpsPending,
+                               psCmdCompleteData->psSrcSync[i].ui32ReadOps2Pending,
                                psCmdCompleteData->psSrcSync[i].ui32WriteOpsPending));
        }
 
        PVR_TTRACE(PVRSRV_TRACE_GROUP_QUEUE, PVRSRV_TRACE_CLASS_CMD_COMP_END,
                        QUEUE_TOKEN_COMMAND_COMPLETE);
 
-       
+       if (psCmdCompleteData->pfnCommandComplete)
+       {
+               psCmdCompleteData->pfnCommandComplete(psCmdCompleteData->hCallbackData);
+       }
+
+       /* free command complete storage */
        psCmdCompleteData->bInUse = IMG_FALSE;
 
-       
+       /* FIXME: This may cause unrelated devices to be woken up. */
        PVRSRVScheduleDeviceCallbacks();
 
        if(bScheduleMISR)
@@ -930,6 +1300,27 @@ IMG_VOID PVRSRVCommandCompleteKM(IMG_HANDLE       hCmdCookie,
 
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRegisterCmdProcListKM
+
+ @Description
+
+ registers a list of private command processing functions with the Command
+ Queue Manager
+
+ @Input                ui32DevIndex : device index
+
+ @Input                 ppfnCmdProcList : function ptr table of private command processors
+
+ @Input                ui32MaxSyncsPerCmd : max number of syncobjects used by command
+
+ @Input                ui32CmdCount : number of entries in function ptr table
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVRegisterCmdProcListKM(IMG_UINT32            ui32DevIndex,
                                                                                 PFN_CMD_PROC   *ppfnCmdProcList,
@@ -943,7 +1334,7 @@ PVRSRV_ERROR PVRSRVRegisterCmdProcListKM(IMG_UINT32                ui32DevIndex,
        DEVICE_COMMAND_DATA             *psDeviceCommandData;
        COMMAND_COMPLETE_DATA   *psCmdCompleteData;
 
-       
+       /* validate device type */
        if(ui32DevIndex >= SYS_DEVICE_COUNT)
        {
                PVR_DPF((PVR_DBG_ERROR,
@@ -952,10 +1343,10 @@ PVRSRV_ERROR PVRSRVRegisterCmdProcListKM(IMG_UINT32              ui32DevIndex,
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* acquire system data structure */
        SysAcquireData(&psSysData);
 
-       
+       /* array of pointers for each command store */
        ui32AllocSize = ui32CmdCount * sizeof(*psDeviceCommandData);
        eError = OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                                ui32AllocSize,
@@ -973,15 +1364,17 @@ PVRSRV_ERROR PVRSRVRegisterCmdProcListKM(IMG_UINT32              ui32DevIndex,
        {
                psDeviceCommandData[ui32CmdTypeCounter].pfnCmdProc = ppfnCmdProcList[ui32CmdTypeCounter];
                psDeviceCommandData[ui32CmdTypeCounter].ui32CCBOffset = 0;
-               
+               psDeviceCommandData[ui32CmdTypeCounter].ui32MaxDstSyncCount = ui32MaxSyncsPerCmd[ui32CmdTypeCounter][0];
+               psDeviceCommandData[ui32CmdTypeCounter].ui32MaxSrcSyncCount = ui32MaxSyncsPerCmd[ui32CmdTypeCounter][1];
                for (ui32CmdCounter = 0; ui32CmdCounter < DC_NUM_COMMANDS_PER_TYPE; ui32CmdCounter++)
                {
-                       
-
-                       ui32AllocSize = sizeof(COMMAND_COMPLETE_DATA) 
+                       /*
+                               allocate storage for the sync update on command complete
+                       */
+                       ui32AllocSize = sizeof(COMMAND_COMPLETE_DATA) /* space for one GENERIC_CMD_COMPLETE */
                                                  + ((ui32MaxSyncsPerCmd[ui32CmdTypeCounter][0]
                                                  +     ui32MaxSyncsPerCmd[ui32CmdTypeCounter][1])
-                                                 * sizeof(PVRSRV_SYNC_OBJECT));         
+                                                 * sizeof(PVRSRV_SYNC_OBJECT));         /* space for max sync objects */
 
                        eError = OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                                                ui32AllocSize,
@@ -996,10 +1389,10 @@ PVRSRV_ERROR PVRSRVRegisterCmdProcListKM(IMG_UINT32              ui32DevIndex,
                        
                        psDeviceCommandData[ui32CmdTypeCounter].apsCmdCompleteData[ui32CmdCounter] = psCmdCompleteData;
                        
-                       
+                       /* clear memory */
                        OSMemSet(psCmdCompleteData, 0x00, ui32AllocSize);
 
-                       
+                       /* setup sync pointers */
                        psCmdCompleteData->psDstSync = (PVRSRV_SYNC_OBJECT*)
                                                                                        (((IMG_UINTPTR_T)psCmdCompleteData)
                                                                                        + sizeof(COMMAND_COMPLETE_DATA));
@@ -1015,7 +1408,7 @@ PVRSRV_ERROR PVRSRVRegisterCmdProcListKM(IMG_UINT32               ui32DevIndex,
 
 ErrorExit:
 
-       
+       /* clean-up if things went wrong */
        if (PVRSRVRemoveCmdProcListKM(ui32DevIndex, ui32CmdCount) != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,
@@ -1027,6 +1420,23 @@ ErrorExit:
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVRemoveCmdProcListKM
+
+ @Description
+
+ removes a list of private command processing functions and data from the
+ Queue Manager
+
+ @Input                ui32DevIndex : device index
+
+ @Input                ui32CmdCount : number of entries in function ptr table
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR PVRSRVRemoveCmdProcListKM(IMG_UINT32 ui32DevIndex,
                                                                           IMG_UINT32 ui32CmdCount)
@@ -1037,7 +1447,7 @@ PVRSRV_ERROR PVRSRVRemoveCmdProcListKM(IMG_UINT32 ui32DevIndex,
        COMMAND_COMPLETE_DATA   *psCmdCompleteData;
        IMG_SIZE_T                              ui32AllocSize;
 
-       
+       /* validate device type */
        if(ui32DevIndex >= SYS_DEVICE_COUNT)
        {
                PVR_DPF((PVR_DBG_ERROR,
@@ -1046,7 +1456,7 @@ PVRSRV_ERROR PVRSRVRemoveCmdProcListKM(IMG_UINT32 ui32DevIndex,
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* acquire system data structure */
        SysAcquireData(&psSysData);
 
        psDeviceCommandData = psSysData->apsDeviceCommandData[ui32DevIndex];
@@ -1058,9 +1468,10 @@ PVRSRV_ERROR PVRSRVRemoveCmdProcListKM(IMG_UINT32 ui32DevIndex,
                        {
                                psCmdCompleteData = psDeviceCommandData[ui32CmdTypeCounter].apsCmdCompleteData[ui32CmdCounter];
                                
-                               
+                               /* free the cmd complete structure array entries */
                                if (psCmdCompleteData != IMG_NULL)
                                {
+                                       PVR_ASSERT(psCmdCompleteData->bInUse == IMG_FALSE);
                                        OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP, psCmdCompleteData->ui32AllocSize,
                                                          psCmdCompleteData, IMG_NULL);
                                        psDeviceCommandData[ui32CmdTypeCounter].apsCmdCompleteData[ui32CmdCounter] = IMG_NULL;
@@ -1068,7 +1479,7 @@ PVRSRV_ERROR PVRSRVRemoveCmdProcListKM(IMG_UINT32 ui32DevIndex,
                        }
                }
 
-               
+               /* free the cmd complete structure array for the device */
                ui32AllocSize = ui32CmdCount * sizeof(*psDeviceCommandData);
                OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP, ui32AllocSize, psDeviceCommandData, IMG_NULL);
                psSysData->apsDeviceCommandData[ui32DevIndex] = IMG_NULL;
@@ -1077,3 +1488,6 @@ PVRSRV_ERROR PVRSRVRemoveCmdProcListKM(IMG_UINT32 ui32DevIndex,
        return PVRSRV_OK;
 }
 
+/******************************************************************************
+ End of file (queue.c)
+******************************************************************************/
index e93f05f..a2a13ab 100644 (file)
@@ -1,28 +1,89 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Resource Allocator
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description
+  Implements generic resource allocation. The resource
+  allocator was originally intended to manage address spaces in
+  practice the resource allocator is generic and can manages arbitrary
+  sets of integers.
+  Resources are allocated from arenas. Arena's can be created with an
+  initial span of resources. Further resources spans can be added to
+  arenas. A call back mechanism allows an arena to request further
+  resource spans on demand.
+  Each arena maintains an ordered list of resource segments each
+  described by a boundary tag. Each boundary tag describes a segment
+  of resources which are either 'free', available for allocation, or
+  'busy' currently allocated. Adjacent 'free' segments are always
+  coallesced to avoid fragmentation.
+  For allocation, all 'free' segments are kept on lists of 'free'
+  segments in a table index by pvr_log2(segment size). ie Each table index
+  n holds 'free' segments in the size range 2**(n-1) -> 2**n.
+  Allocation policy is based on an *almost* best fit
+  stratedy. Choosing any segment from the appropriate table entry
+  guarantees that we choose a segment which is with a power of 2 of
+  the size we are allocating.
+  Allocated segments are inserted into a self scaling hash table which
+  maps the base resource of the span to the relevant boundary
+  tag. This allows the code to get back to the bounary tag without
+  exporting explicit boundary tag references through the API.
+  Each arena has an associated quantum size, all allocations from the
+  arena are made in multiples of the basic quantum.
+  On resource exhaustion in an arena, a callback if provided will be
+  used to request further resources. Resouces spans allocated by the
+  callback mechanism are delimited by special boundary tag markers of
+  zero span, 'span' markers. Span markers are never coallesced. Span
+  markers are used to detect when an imported span is completely free
+  and can be deallocated by the callback mechanism.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+/* Issues:
+ * - flags, flags are passed into the resource allocator but are not currently used.
+ * - determination, of import size, is currently braindead.
+ * - debug code should be moved out to own module and #ifdef'd
+ */
 
 #include "services_headers.h"
 #include "hash.h"
@@ -30,7 +91,7 @@
 #include "buffer_manager.h"
 #include "osfunc.h"
 
-#ifdef __linux__
+#if defined(__linux__) && defined(__KERNEL__)
 #include <linux/kernel.h>
 #include "proc.h"
 #endif
 #include <stdio.h>
 #endif
 
+/* The initial, and minimum size of the live address -> boundary tag
+   structure hash table. The value 64 is a fairly arbitrary
+   choice. The hash table resizes on demand so the value choosen is
+   not critical. */
 #define MINIMUM_HASH_SIZE (64)
 
 #if defined(VALIDATE_ARENA_TEST)
 
+/* This test validates the doubly linked ordered list of boundary tags, by
+checking that adjacent members of the list have compatible eResourceSpan
+and eResourceType values. */
+
 typedef enum RESOURCE_DESCRIPTOR_TAG {
 
        RESOURCE_SPAN_LIVE                              = 10,
@@ -67,33 +136,36 @@ static IMG_UINT32 ui32BoundaryTagID = 0;
 IMG_UINT32 ValidateArena(RA_ARENA *pArena);
 #endif
 
+/* boundary tags, used to describe a resource segment */
 struct _BT_
 {
        enum bt_type
        {
-               btt_span,                               
-               btt_free,                               
-               btt_live                                
+               btt_span,                               /* span markers */
+               btt_free,                               /* free resource segment */
+               btt_live                                /* allocated resource segment */
        } type;
 
-       
+       /* The base resource and extent of this segment */
        IMG_UINTPTR_T base;
        IMG_SIZE_T uSize;
 
-       
+       /* doubly linked ordered list of all segments within the arena */
        struct _BT_ *pNextSegment;
        struct _BT_ *pPrevSegment;
-       
+       /* doubly linked un-ordered list of free segments. */
        struct _BT_ *pNextFree;
        struct _BT_ *pPrevFree;
-       
+       /* a user reference associated with this span, user references are
+        * currently only provided in the callback mechanism */
        BM_MAPPING *psMapping;
 
 #if defined(VALIDATE_ARENA_TEST)
        RESOURCE_DESCRIPTOR eResourceSpan;
        RESOURCE_TYPE           eResourceType;
 
-       
+       /* This variable provides a reference (used in debug messages) to incompatible
+       boundary tags within the doubly linked ordered list. */
        IMG_UINT32                      ui32BoundaryTagID;
 #endif
 
@@ -101,40 +173,45 @@ struct _BT_
 typedef struct _BT_ BT;
 
 
+/* resource allocation arena */
 struct _RA_ARENA_
 {
-       
+       /* arena name for diagnostics output */
        IMG_CHAR *name;
 
-       
+       /* allocations within this arena are quantum sized */
        IMG_SIZE_T uQuantum;
 
-       
+       /* import interface, if provided */
        IMG_BOOL (*pImportAlloc)(IMG_VOID *,
                                                         IMG_SIZE_T uSize,
                                                         IMG_SIZE_T *pActualSize,
                                                         BM_MAPPING **ppsMapping,
                                                         IMG_UINT32 uFlags,
+                                                        IMG_PVOID pvPrivData,
+                                                        IMG_UINT32 ui32PrivDataLength,
                                                         IMG_UINTPTR_T *pBase);
        IMG_VOID (*pImportFree) (IMG_VOID *,
                                                 IMG_UINTPTR_T,
                                                 BM_MAPPING *psMapping);
        IMG_VOID (*pBackingStoreFree) (IMG_VOID *, IMG_SIZE_T, IMG_SIZE_T, IMG_HANDLE);
 
-       
+       /* arbitrary handle provided by arena owner to be passed into the
+        * import alloc and free hooks */
        IMG_VOID *pImportHandle;
 
-       
+       /* head of list of free boundary tags for indexed by pvr_log2 of the
+          boundary tag size */
 #define FREE_TABLE_LIMIT 32
 
-       
+       /* power-of-two table of free lists */
        BT *aHeadFree [FREE_TABLE_LIMIT];
 
-       
+       /* resource ordered segment list */
        BT *pHeadSegment;
        BT *pTailSegment;
 
-       
+       /* segment address to boundary tag hash table */
        HASH_TABLE *pSegmentHash;
 
 #ifdef RA_STATS
@@ -150,6 +227,7 @@ struct _RA_ARENA_
        IMG_BOOL bInitProcEntry;
 #endif
 };
+/* #define ENABLE_RA_DUMP      1 */
 #if defined(ENABLE_RA_DUMP)
 IMG_VOID RA_Dump (RA_ARENA *pArena);
 #endif
@@ -162,7 +240,7 @@ static void* RA_ProcSeqOff2ElementInfo(struct seq_file * sfile, loff_t off);
 static void RA_ProcSeqShowRegs(struct seq_file *sfile, void* el);
 static void* RA_ProcSeqOff2ElementRegs(struct seq_file * sfile, loff_t off);
 
-#endif 
+#endif /* defined(CONFIG_PROC_FS) && defined(DEBUG) */
 
 #ifdef USE_BM_FREESPACE_CHECK
 IMG_VOID CheckBMFreespace(IMG_VOID);
@@ -185,12 +263,33 @@ static IMG_CHAR *ReplaceSpaces(IMG_CHAR * const pS)
 }
 #endif
 
+/*!
+******************************************************************************
+       @Function       _RequestAllocFail
+
+       @Description    Default callback allocator used if no callback is
+                    specified, always fails to allocate further resources to the
+                    arena.
+
+       @Input          _h - callback handle
+       @Input          _uSize - requested allocation size
+       @Output         _pActualSize - actual allocation size
+       @Input          _pRef - user reference
+       @Input          _uflags - allocation flags
+       @Input          _pvPrivData - private data
+       @Input          _ui32PrivDataLength - private data length
+       @Input          _pBase - receives allocated base
+
+       @Return         IMG_FALSE, this function always fails to allocate.
+******************************************************************************/
 static IMG_BOOL
 _RequestAllocFail (IMG_VOID *_h,
                                  IMG_SIZE_T _uSize,
                                  IMG_SIZE_T *_pActualSize,
                                  BM_MAPPING **_ppsMapping,
                                  IMG_UINT32 _uFlags,
+                                 IMG_PVOID _pvPrivData,
+                                 IMG_UINT32 _ui32PrivDataLength,
                                  IMG_UINTPTR_T *_pBase)
 {
        PVR_UNREFERENCED_PARAMETER (_h);
@@ -199,10 +298,22 @@ _RequestAllocFail (IMG_VOID *_h,
        PVR_UNREFERENCED_PARAMETER (_ppsMapping);
        PVR_UNREFERENCED_PARAMETER (_uFlags);
        PVR_UNREFERENCED_PARAMETER (_pBase);
+       PVR_UNREFERENCED_PARAMETER (_pvPrivData);
+       PVR_UNREFERENCED_PARAMETER (_ui32PrivDataLength);
 
        return IMG_FALSE;
 }
 
+/*!
+******************************************************************************
+       @Function       pvr_log2
+
+       @Description    Computes the floor of the log base 2 of a unsigned integer
+
+       @Input          n - unsigned integer
+
+       @Return         Floor(Log2(n))
+******************************************************************************/
 static IMG_UINT32
 pvr_log2 (IMG_SIZE_T n)
 {
@@ -216,6 +327,19 @@ pvr_log2 (IMG_SIZE_T n)
        return l;
 }
 
+/*!
+******************************************************************************
+       @Function       _SegmentListInsertAfter
+
+       @Description    Insert a boundary tag into an arena segment list after a
+                    specified boundary tag.
+
+       @Input          pArena - the arena.
+       @Input          pInsertionPoint - the insertion point.
+       @Input          pBT - the boundary tag to insert.
+
+       @Return         PVRSRV_ERROR
+******************************************************************************/
 static PVRSRV_ERROR
 _SegmentListInsertAfter (RA_ARENA *pArena,
                                                 BT *pInsertionPoint,
@@ -241,12 +365,24 @@ _SegmentListInsertAfter (RA_ARENA *pArena,
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+       @Function       _SegmentListInsert
+
+       @Description    Insert a boundary tag into an arena segment list at the
+                    appropriate point.
+
+       @Input          pArena - the arena.
+       @Input          pBT - the boundary tag to insert.
+
+       @Return         None
+******************************************************************************/
 static PVRSRV_ERROR
 _SegmentListInsert (RA_ARENA *pArena, BT *pBT)
 {
        PVRSRV_ERROR eError = PVRSRV_OK;
 
-       
+       /* insert into the segment chain */
        if (pArena->pHeadSegment == IMG_NULL)
        {
                pArena->pHeadSegment = pArena->pTailSegment = pBT;
@@ -258,7 +394,8 @@ _SegmentListInsert (RA_ARENA *pArena, BT *pBT)
 
                if (pBT->base < pArena->pHeadSegment->base)
                {
-                       
+                       /* The base address of pBT is less than the base address of the boundary tag
+                       at the head of the list - so insert this boundary tag at the head. */
                        pBT->pNextSegment = pArena->pHeadSegment;
                        pArena->pHeadSegment->pPrevSegment = pBT;
                        pArena->pHeadSegment = pBT;
@@ -267,9 +404,10 @@ _SegmentListInsert (RA_ARENA *pArena, BT *pBT)
                else
                {
 
-                       
-
-
+                       /* The base address of pBT is greater than or equal to that of the boundary tag
+                       at the head of the list. Search for the insertion point: pBT must be inserted
+                       before the first boundary tag with a greater base value - or at the end of the list.
+                       */
                        pBTScan = pArena->pHeadSegment;
 
                        while ((pBTScan->pNextSegment != IMG_NULL)  && (pBT->base >= pBTScan->pNextSegment->base))
@@ -287,6 +425,17 @@ _SegmentListInsert (RA_ARENA *pArena, BT *pBT)
        return eError;
 }
 
+/*!
+******************************************************************************
+       @Function       _SegmentListRemove
+
+       @Description    Remove a boundary tag from an arena segment list.
+
+       @Input          pArena - the arena.
+       @Input          pBT - the boundary tag to remove.
+
+       @Return         None
+******************************************************************************/
 static IMG_VOID
 _SegmentListRemove (RA_ARENA *pArena, BT *pBT)
 {
@@ -301,6 +450,23 @@ _SegmentListRemove (RA_ARENA *pArena, BT *pBT)
                pBT->pNextSegment->pPrevSegment = pBT->pPrevSegment;
 }
 
+/*!
+******************************************************************************
+       @Function       _SegmentSplit
+
+       @Description    Split a segment into two, maintain the arena segment list. The
+                    boundary tag should not be in the free table. Neither the
+                    original or the new neighbour bounary tag will be in the free
+                    table.
+
+       @Input          pArena - the arena.
+       @Input          pBT - the boundary tag to split.
+       @Input          uSize - the required segment size of boundary tag after
+                            splitting.
+
+       @Return         New neighbour boundary tag.
+
+******************************************************************************/
 static BT *
 _SegmentSplit (RA_ARENA *pArena, BT *pBT, IMG_SIZE_T uSize)
 {
@@ -363,6 +529,18 @@ _SegmentSplit (RA_ARENA *pArena, BT *pBT, IMG_SIZE_T uSize)
        return pNeighbour;
 }
 
+/*!
+******************************************************************************
+       @Function       _FreeListInsert
+
+       @Description    Insert a boundary tag into an arena free table.
+
+       @Input          pArena - the arena.
+       @Input          pBT - the boundary tag.
+
+       @Return         None
+
+******************************************************************************/
 static IMG_VOID
 _FreeListInsert (RA_ARENA *pArena, BT *pBT)
 {
@@ -376,6 +554,18 @@ _FreeListInsert (RA_ARENA *pArena, BT *pBT)
        pArena->aHeadFree [uIndex] = pBT;
 }
 
+/*!
+******************************************************************************
+       @Function       _FreeListRemove
+
+       @Description    Remove a boundary tag from an arena free table.
+
+       @Input          pArena - the arena.
+       @Input          pBT - the boundary tag.
+
+       @Return         None
+
+******************************************************************************/
 static IMG_VOID
 _FreeListRemove (RA_ARENA *pArena, BT *pBT)
 {
@@ -389,6 +579,18 @@ _FreeListRemove (RA_ARENA *pArena, BT *pBT)
                pBT->pPrevFree->pNextFree = pBT->pNextFree;
 }
 
+/*!
+******************************************************************************
+       @Function       _BuildSpanMarker
+
+       @Description    Construct a span marker boundary tag.
+
+       @Input          pArena - arena to contain span marker
+       @Input          base - the base of the bounary tag.
+
+       @Return         span marker boundary tag
+
+******************************************************************************/
 static BT *
 _BuildSpanMarker (IMG_UINTPTR_T base, IMG_SIZE_T uSize)
 {
@@ -416,6 +618,18 @@ _BuildSpanMarker (IMG_UINTPTR_T base, IMG_SIZE_T uSize)
        return pBT;
 }
 
+/*!
+******************************************************************************
+       @Function       _BuildBT
+
+       @Description    Construct a boundary tag for a free segment.
+
+       @Input          base - the base of the resource segment.
+       @Input          uSize - the extent of the resouce segment.
+
+       @Return         boundary tag
+
+******************************************************************************/
 static BT *
 _BuildBT (IMG_UINTPTR_T base, IMG_SIZE_T uSize)
 {
@@ -442,6 +656,20 @@ _BuildBT (IMG_UINTPTR_T base, IMG_SIZE_T uSize)
        return pBT;
 }
 
+/*!
+******************************************************************************
+       @Function       _InsertResource
+
+       @Description    Add a free resource segment to an arena.
+
+       @Input          pArena - the arena.
+       @Input          base - the base of the resource segment.
+       @Input          uSize - the extent of the resource segment.
+
+       @Return         New bucket pointer
+                    IMG_NULL failure
+
+******************************************************************************/
 static BT *
 _InsertResource (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_SIZE_T uSize)
 {
@@ -477,6 +705,19 @@ _InsertResource (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_SIZE_T uSize)
        return pBT;
 }
 
+/*!
+******************************************************************************
+       @Function       _InsertResourceSpan
+
+       @Description    Add a free resource span to an arena, complete with span markers.
+
+       @Input          pArena - the arena.
+       @Input          base - the base of the resource segment.
+       @Input          uSize - the extent of the resource segment.
+
+       @Return         the boundary tag representing the free resource segment,
+                    or IMG_NULL on failure.
+******************************************************************************/
 static BT *
 _InsertResourceSpan (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_SIZE_T uSize)
 {
@@ -551,22 +792,40 @@ _InsertResourceSpan (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_SIZE_T uSize)
 
 #ifdef RA_STATS
        pArena->sStatistics.uTotalResourceCount+=uSize;
+/*     pArena->sStatistics.uFreeResourceCount+=uSize;
+       This has got to be wrong as uFreeResourceCount ends
+       up larger than uTotalResourceCount by uTotalResourceCount
+       - allocated memory
+*/
 #endif
        return pBT;
 
   fail_SegListInsert:
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), pBT, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
   fail_bt:
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), pSpanEnd, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
   fail_end:
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), pSpanStart, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
   fail_start:
        return IMG_NULL;
 }
 
+/*!
+******************************************************************************
+       @Function       _FreeBT
+
+       @Description    Free a boundary tag taking care of the segment list and the
+                    boundary tag free table.
+
+       @Input          pArena - the arena.
+       @Input          pBT - the boundary tag to free.
+       @Input          bFreeBackingStore - Should backing for the memory be freed
+                                                                                as well.
+       @Return         None
+******************************************************************************/
 static IMG_VOID
 _FreeBT (RA_ARENA *pArena, BT *pBT, IMG_BOOL bFreeBackingStore)
 {
@@ -592,7 +851,7 @@ _FreeBT (RA_ARENA *pArena, BT *pBT, IMG_BOOL bFreeBackingStore)
        uOrigBase = pBT->base;
        uOrigSize = pBT->uSize;
 
-       
+       /* try and coalesce with left neighbour */
        pNeighbour = pBT->pPrevSegment;
        if (pNeighbour!=IMG_NULL
                && pNeighbour->type == btt_free
@@ -603,13 +862,13 @@ _FreeBT (RA_ARENA *pArena, BT *pBT, IMG_BOOL bFreeBackingStore)
                pBT->base = pNeighbour->base;
                pBT->uSize += pNeighbour->uSize;
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), pNeighbour, IMG_NULL);
-               
+               /*not nulling original pointer, already overwritten*/
 #ifdef RA_STATS
                pArena->sStatistics.uFreeSegmentCount--;
 #endif
        }
 
-       
+       /* try to coalesce with right neighbour */
        pNeighbour = pBT->pNextSegment;
        if (pNeighbour!=IMG_NULL
                && pNeighbour->type == btt_free
@@ -619,28 +878,28 @@ _FreeBT (RA_ARENA *pArena, BT *pBT, IMG_BOOL bFreeBackingStore)
                _SegmentListRemove (pArena, pNeighbour);
                pBT->uSize += pNeighbour->uSize;
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), pNeighbour, IMG_NULL);
-               
+               /*not nulling original pointer, already overwritten*/
 #ifdef RA_STATS
                pArena->sStatistics.uFreeSegmentCount--;
 #endif
        }
 
-       
+       /* try to free backing store memory. */
        if (pArena->pBackingStoreFree != IMG_NULL && bFreeBackingStore)
        {
                IMG_UINTPTR_T   uRoundedStart, uRoundedEnd;
 
-               
+               /* Work out the first address we might be able to free. */
                uRoundedStart = (uOrigBase / pArena->uQuantum) * pArena->uQuantum;
-               
+               /* If a span is still using that address then leave it. */
                if (uRoundedStart < pBT->base)
                {
                        uRoundedStart += pArena->uQuantum;
                }
 
-               
+               /* Work out the last address we might be able to free. */
                uRoundedEnd = ((uOrigBase + uOrigSize + pArena->uQuantum - 1) / pArena->uQuantum) * pArena->uQuantum;
-               
+               /* If a span is still using that addres then leave it. */
                if (uRoundedEnd > (pBT->base + pBT->uSize))
                {
                        uRoundedEnd -= pArena->uQuantum;
@@ -669,17 +928,35 @@ _FreeBT (RA_ARENA *pArena, BT *pBT, IMG_BOOL bFreeBackingStore)
                pArena->sStatistics.uTotalResourceCount-=pBT->uSize;
 #endif
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), next, IMG_NULL);
-               
+               /*not nulling original pointer, already overwritten*/
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), prev, IMG_NULL);
-               
+               /*not nulling original pointer, already overwritten*/
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), pBT, IMG_NULL);
-               
+               /*not nulling pointer, copy on stack*/
        }
        else
                _FreeListInsert (pArena, pBT);
 }
 
 
+/*!
+******************************************************************************
+       @Function       _AttemptAllocAligned
+
+       @Description    Attempt an allocation from an arena.
+
+       @Input          pArena - the arena.
+       @Input          uSize - the requested allocation size.
+       @Output         ppsMapping - the user references associated with
+                        the allocated segment.
+       @Input          flags - allocation flags
+       @Input          uAlignment - required uAlignment, or 0
+       @Input          uAlignmentOffset
+       @Output         base - allocated resource base
+
+       @Return         IMG_FALSE failure
+                    IMG_TRUE success
+******************************************************************************/
 static IMG_BOOL
 _AttemptAllocAligned (RA_ARENA *pArena,
                                          IMG_SIZE_T uSize,
@@ -700,16 +977,11 @@ _AttemptAllocAligned (RA_ARENA *pArena,
        if (uAlignment>1)
                uAlignmentOffset %= uAlignment;
 
-       
-
+       /* search for a near fit free boundary tag, start looking at the
+          pvr_log2 free table for our required size and work on up the
+          table. */
        uIndex = pvr_log2 (uSize);
 
-#if 0
-       
-       if (1u<<uIndex < uSize)
-               uIndex++;
-#endif
-
        while (uIndex < FREE_TABLE_LIMIT && pArena->aHeadFree[uIndex]==IMG_NULL)
                uIndex++;
 
@@ -717,7 +989,7 @@ _AttemptAllocAligned (RA_ARENA *pArena,
        {
                if (pArena->aHeadFree[uIndex]!=IMG_NULL)
                {
-                       
+                       /* we have a cached free boundary tag */
                        BT *pBT;
 
                        pBT = pArena->aHeadFree [uIndex];
@@ -748,16 +1020,16 @@ _AttemptAllocAligned (RA_ARENA *pArena,
                                                pArena->sStatistics.uFreeResourceCount-=pBT->uSize;
 #endif
 
-                                               
+                                               /* with uAlignment we might need to discard the front of this segment */
                                                if (aligned_base > pBT->base)
                                                {
                                                        BT *pNeighbour;
                                                        pNeighbour = _SegmentSplit (pArena, pBT, (IMG_SIZE_T)(aligned_base - pBT->base));
-                                                       
+                                                       /* partition the buffer, create a new boundary tag */
                                                        if (pNeighbour==IMG_NULL)
                                                        {
                                                                PVR_DPF ((PVR_DBG_ERROR,"_AttemptAllocAligned: Front split failed"));
-                                                               
+                                                               /* Put pBT back in the list */
                                                                _FreeListInsert (pArena, pBT);
                                                                return IMG_FALSE;
                                                        }
@@ -770,16 +1042,16 @@ _AttemptAllocAligned (RA_ARENA *pArena,
                                                        pBT = pNeighbour;
                                                }
 
-                                               
+                                               /* the segment might be too big, if so, discard the back of the segment */
                                                if (pBT->uSize > uSize)
                                                {
                                                        BT *pNeighbour;
                                                        pNeighbour = _SegmentSplit (pArena, pBT, uSize);
-                                                       
+                                                       /* partition the buffer, create a new boundary tag */
                                                        if (pNeighbour==IMG_NULL)
                                                        {
                                                                PVR_DPF ((PVR_DBG_ERROR,"_AttemptAllocAligned: Back split failed"));
-                                                               
+                                                               /* Put pBT back in the list */
                                                                _FreeListInsert (pArena, pBT);
                                                                return IMG_FALSE;
                                                        }
@@ -840,6 +1112,23 @@ _AttemptAllocAligned (RA_ARENA *pArena,
 
 
 
+/*!
+******************************************************************************
+       @Function       RA_Create
+
+       @Description    To create a resource arena.
+
+       @Input          name - the name of the arena for diagnostic purposes.
+       @Input          base - the base of an initial resource span or 0.
+       @Input          uSize - the size of an initial resource span or 0.
+       @Input          uQuantum - the arena allocation quantum.
+       @Input          alloc - a resource allocation callback or 0.
+       @Input          free - a resource de-allocation callback or 0.
+       @Input          backingstore_free - a callback to free resources for spans or 0.
+       @Input          pImportHandle - handle passed to alloc and free or 0.
+
+       @Return         arena handle, or IMG_NULL.
+******************************************************************************/
 RA_ARENA *
 RA_Create (IMG_CHAR *name,
                   IMG_UINTPTR_T base,
@@ -847,7 +1136,9 @@ RA_Create (IMG_CHAR *name,
                   BM_MAPPING *psMapping,
                   IMG_SIZE_T uQuantum,
                   IMG_BOOL (*imp_alloc)(IMG_VOID *, IMG_SIZE_T uSize, IMG_SIZE_T *pActualSize,
-                                    BM_MAPPING **ppsMapping, IMG_UINT32 _flags, IMG_UINTPTR_T *pBase),
+                                                                BM_MAPPING **ppsMapping, IMG_UINT32 _flags,
+                                                                IMG_PVOID pvPrivData, IMG_UINT32 ui32PrivDataLength,
+                                                                IMG_UINTPTR_T *pBase),
                   IMG_VOID (*imp_free) (IMG_VOID *, IMG_UINTPTR_T, BM_MAPPING *),
                   IMG_VOID (*backingstore_free) (IMG_VOID*, IMG_SIZE_T, IMG_SIZE_T, IMG_HANDLE),
                   IMG_VOID *pImportHandle)
@@ -908,7 +1199,7 @@ RA_Create (IMG_CHAR *name,
 
                pArena->bInitProcEntry = !PVRSRVGetInitServerState(PVRSRV_INIT_SERVER_SUCCESSFUL);
 
-               
+               /* Don't put shared heap info into a per process /proc subdirectory */
                pfnCreateProcEntrySeq = pArena->bInitProcEntry ? CreateProcEntrySeq : CreatePerProcessProcEntrySeq;
 
                ret = snprintf(szProcInfoName, sizeof(szProcInfoName), "ra_info_%s", pArena->name);
@@ -935,7 +1226,7 @@ RA_Create (IMG_CHAR *name,
                        PVR_DPF((PVR_DBG_ERROR, "RA_Create: couldn't create ra_segs proc entry for arena %s", pArena->name));
                }
        }
-#endif 
+#endif /* defined(CONFIG_PROC_FS) && defined(DEBUG) */
 
        pArena->pSegmentHash = HASH_Create (MINIMUM_HASH_SIZE);
        if (pArena->pSegmentHash==IMG_NULL)
@@ -959,11 +1250,22 @@ insert_fail:
        HASH_Delete (pArena->pSegmentHash);
 hash_fail:
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(RA_ARENA), pArena, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
 arena_fail:
        return IMG_NULL;
 }
 
+/*!
+******************************************************************************
+       @Function       RA_Delete
+
+       @Description    To delete a resource arena. All resources allocated from
+                    the arena must be freed before deleting the arena.
+
+       @Input          pArena - the arena to delete.
+
+       @Return         None
+******************************************************************************/
 IMG_VOID
 RA_Delete (RA_ARENA *pArena)
 {
@@ -996,7 +1298,7 @@ RA_Delete (RA_ARENA *pArena)
 
                _SegmentListRemove (pArena, pBT);
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(BT), pBT, IMG_NULL);
-               
+               /*not nulling original pointer, it has changed*/
 #ifdef RA_STATS
                pArena->sStatistics.uSpanCount--;
 #endif
@@ -1020,9 +1322,20 @@ RA_Delete (RA_ARENA *pArena)
 #endif
        HASH_Delete (pArena->pSegmentHash);
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(RA_ARENA), pArena, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 }
 
+/*!
+******************************************************************************
+       @Function       RA_TestDelete
+
+       @Description    To test whether it is safe to delete a resource arena. If any
+                    allocations have not been freed, the RA must not be deleted.
+
+       @Input          pArena - the arena to test.
+
+       @Return         IMG_BOOL - IMG_TRUE if is safe to go on and call RA_Delete.
+******************************************************************************/
 IMG_BOOL
 RA_TestDelete (RA_ARENA *pArena)
 {
@@ -1045,6 +1358,20 @@ RA_TestDelete (RA_ARENA *pArena)
        return IMG_TRUE;
 }
 
+/*!
+******************************************************************************
+       @Function       RA_Add
+
+       @Description    To add a resource span to an arena. The span must not
+                    overlapp with any span previously added to the arena.
+
+       @Input          pArena - the arena to add a span into.
+       @Input          base - the base of the span.
+       @Input          uSize - the extent of the span.
+
+       @Return         IMG_TRUE - Success
+                    IMG_FALSE - failure
+******************************************************************************/
 IMG_BOOL
 RA_Add (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_SIZE_T uSize)
 {
@@ -1063,6 +1390,29 @@ RA_Add (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_SIZE_T uSize)
        return ((IMG_BOOL)(_InsertResource (pArena, base, uSize) != IMG_NULL));
 }
 
+/*!
+******************************************************************************
+       @Function       RA_Alloc
+
+       @Description    To allocate resource from an arena.
+
+       @Input          pArena - the arena
+       @Input          uRequestSize - the size of resource segment requested.
+       @Output         pActualSize - the actual size of resource segment
+                     allocated, typcially rounded up by quantum.
+       @Output         ppsMapping - the user reference associated with allocated resource span.
+       @Input          uFlags - flags influencing allocation policy.
+       @Input          uAlignment - the uAlignment constraint required for the
+                            allocated segment, use 0 if uAlignment not required.
+       @Input          uAlignmentOffset
+       @Input          pvPrivData - opaque private data passed through to allocator
+       @Input          ui32PrivDataLength - length of opaque private data
+
+       @Output         base - allocated base resource
+
+       @Return         IMG_TRUE - success
+                    IMG_FALSE - failure
+******************************************************************************/
 IMG_BOOL
 RA_Alloc (RA_ARENA *pArena,
                  IMG_SIZE_T uRequestSize,
@@ -1071,6 +1421,8 @@ RA_Alloc (RA_ARENA *pArena,
                  IMG_UINT32 uFlags,
                  IMG_UINT32 uAlignment,
                  IMG_UINT32 uAlignmentOffset,
+                 IMG_PVOID pvPrivData,
+                 IMG_UINT32 ui32PrivDataLength,
                  IMG_UINTPTR_T *base)
 {
        IMG_BOOL bResult;
@@ -1101,8 +1453,9 @@ RA_Alloc (RA_ARENA *pArena,
                          "RA_Alloc: arena='%s', size=0x%x(0x%x), alignment=0x%x, offset=0x%x",
                   pArena->name, uSize, uRequestSize, uAlignment, uAlignmentOffset));
 
-       
-
+       /* if allocation failed then we might have an import source which
+          can provide more resource, else we will have to fail the
+          allocation to the caller. */
        bResult = _AttemptAllocAligned (pArena, uSize, ppsMapping, uFlags,
                                                                        uAlignment, uAlignmentOffset, base);
        if (!bResult)
@@ -1111,34 +1464,38 @@ RA_Alloc (RA_ARENA *pArena,
                IMG_UINTPTR_T import_base;
                IMG_SIZE_T uImportSize = uSize;
 
-               
-
-
+               /*
+                       Ensure that we allocate sufficient space to meet the uAlignment
+                       constraint
+                */
                if (uAlignment > pArena->uQuantum)
                {
                        uImportSize += (uAlignment - 1);
                }
 
-               
+               /* ensure that we import according to the quanta of this arena */
                uImportSize = ((uImportSize + pArena->uQuantum - 1)/pArena->uQuantum)*pArena->uQuantum;
 
                bResult =
                        pArena->pImportAlloc (pArena->pImportHandle, uImportSize, &uImportSize,
-                                                                &psImportMapping, uFlags, &import_base);
+                                                                 &psImportMapping, uFlags,
+                                                                 pvPrivData, ui32PrivDataLength, &import_base);
                if (bResult)
                {
                        BT *pBT;
                        pBT = _InsertResourceSpan (pArena, import_base, uImportSize);
-                       
+                       /* successfully import more resource, create a span to
+                          represent it and retry the allocation attempt */
                        if (pBT == IMG_NULL)
                        {
-                               
+                               /* insufficient resources to insert the newly acquired span,
+                                  so free it back again */
                                pArena->pImportFree(pArena->pImportHandle, import_base,
                                                                        psImportMapping);
                                PVR_DPF ((PVR_DBG_MESSAGE,
                                                  "RA_Alloc: name='%s', size=0x%x failed!",
                                                  pArena->name, uSize));
-                               
+                               /* RA_Dump (arena); */
                                return IMG_FALSE;
                        }
                        pBT->psMapping = psImportMapping;
@@ -1168,7 +1525,9 @@ RA_Alloc (RA_ARENA *pArena,
                          "RA_Alloc: name='%s', size=0x%x, *base=0x%x = %d",
                          pArena->name, uSize, *base, bResult));
 
-       
+       /*  RA_Dump (pArena);
+               ra_stats (pArena);
+       */
 
 #if defined(VALIDATE_ARENA_TEST)
        ValidateArena(pArena);
@@ -1180,6 +1539,20 @@ RA_Alloc (RA_ARENA *pArena,
 
 #if defined(VALIDATE_ARENA_TEST)
 
+/*!
+******************************************************************************
+       @Function       ValidateArena
+
+       @Description    Validate an arena by checking that adjacent members of the
+                    double linked ordered list are compatible. PVR_DBG_BREAK and
+                    PVR_DPF messages are used when an error is detected.
+                    NOTE: A DEBUG build is required for PVR_DBG_BREAK and PVR_DPF
+                    to operate.
+
+       @Input          pArena - the arena
+
+       @Return         0
+******************************************************************************/
 IMG_UINT32 ValidateArena(RA_ARENA *pArena)
 {
        BT* pSegment;
@@ -1208,7 +1581,7 @@ IMG_UINT32 ValidateArena(RA_ARENA *pArena)
                                                  (eNextSpan == IMPORTED_RESOURCE_SPAN_FREE) ||
                                                  (eNextSpan == IMPORTED_RESOURCE_SPAN_END)))
                                        {
-                                               
+                                               /* error - next span must be live, free or end */
                                                PVR_DPF((PVR_DBG_ERROR, "ValidateArena ERROR: adjacent boundary tags %d (base=0x%x) and %d (base=0x%x) are incompatible (arena: %s)",
                                                                pSegment->ui32BoundaryTagID, pSegment->base, pSegment->pNextSegment->ui32BoundaryTagID, pSegment->pNextSegment->base, pArena->name));
 
@@ -1221,7 +1594,7 @@ IMG_UINT32 ValidateArena(RA_ARENA *pArena)
                                        if (!((eNextSpan == IMPORTED_RESOURCE_SPAN_LIVE) ||
                                                  (eNextSpan == IMPORTED_RESOURCE_SPAN_END)))
                                        {
-                                               
+                                               /* error - next span must be live or end */
                                                PVR_DPF((PVR_DBG_ERROR, "ValidateArena ERROR: adjacent boundary tags %d (base=0x%x) and %d (base=0x%x) are incompatible (arena: %s)",
                                                                pSegment->ui32BoundaryTagID, pSegment->base, pSegment->pNextSegment->ui32BoundaryTagID, pSegment->pNextSegment->base, pArena->name));
 
@@ -1235,7 +1608,7 @@ IMG_UINT32 ValidateArena(RA_ARENA *pArena)
                                                (eNextSpan == IMPORTED_RESOURCE_SPAN_FREE) ||
                                                (eNextSpan == IMPORTED_RESOURCE_SPAN_END))
                                        {
-                                               
+                                               /* error - next span cannot be live, free or end */
                                                PVR_DPF((PVR_DBG_ERROR, "ValidateArena ERROR: adjacent boundary tags %d (base=0x%x) and %d (base=0x%x) are incompatible (arena: %s)",
                                                                pSegment->ui32BoundaryTagID, pSegment->base, pSegment->pNextSegment->ui32BoundaryTagID, pSegment->pNextSegment->base, pArena->name));
 
@@ -1249,7 +1622,7 @@ IMG_UINT32 ValidateArena(RA_ARENA *pArena)
                                        if (!((eNextSpan == IMPORTED_RESOURCE_SPAN_LIVE) ||
                                                  (eNextSpan == IMPORTED_RESOURCE_SPAN_FREE)))
                                        {
-                                               
+                                               /* error - next span must be live or free */
                                                PVR_DPF((PVR_DBG_ERROR, "ValidateArena ERROR: adjacent boundary tags %d (base=0x%x) and %d (base=0x%x) are incompatible (arena: %s)",
                                                                pSegment->ui32BoundaryTagID, pSegment->base, pSegment->pNextSegment->ui32BoundaryTagID, pSegment->pNextSegment->base, pArena->name));
 
@@ -1282,7 +1655,7 @@ IMG_UINT32 ValidateArena(RA_ARENA *pArena)
                                        if (!((eNextSpan == RESOURCE_SPAN_FREE) ||
                                                  (eNextSpan == RESOURCE_SPAN_LIVE)))
                                        {
-                                               
+                                               /* error - next span must be free or live */
                                                PVR_DPF((PVR_DBG_ERROR, "ValidateArena ERROR: adjacent boundary tags %d (base=0x%x) and %d (base=0x%x) are incompatible (arena: %s)",
                                                                pSegment->ui32BoundaryTagID, pSegment->base, pSegment->pNextSegment->ui32BoundaryTagID, pSegment->pNextSegment->base, pArena->name));
 
@@ -1295,7 +1668,7 @@ IMG_UINT32 ValidateArena(RA_ARENA *pArena)
                                        if (!((eNextSpan == RESOURCE_SPAN_FREE) ||
                                                  (eNextSpan == RESOURCE_SPAN_LIVE)))
                                        {
-                                               
+                                               /* error - next span must be free or live */
                                                PVR_DPF((PVR_DBG_ERROR, "ValidateArena ERROR: adjacent boundary tags %d (base=0x%x) and %d (base=0x%x) are incompatible (arena: %s)",
                                                                pSegment->ui32BoundaryTagID, pSegment->base, pSegment->pNextSegment->ui32BoundaryTagID, pSegment->pNextSegment->base, pArena->name));
 
@@ -1327,6 +1700,18 @@ IMG_UINT32 ValidateArena(RA_ARENA *pArena)
 #endif
 
 
+/*!
+******************************************************************************
+       @Function       RA_Free
+
+       @Description    To free a resource segment.
+
+       @Input          pArena - the arena the segment was originally allocated from.
+       @Input          base - the base of the resource span to free.
+       @Input          bFreeBackingStore - Should backing store memory be freed.
+
+       @Return         None
+******************************************************************************/
 IMG_VOID
 RA_Free (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_BOOL bFreeBackingStore)
 {
@@ -1386,6 +1771,17 @@ RA_Free (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_BOOL bFreeBackingStore)
 }
 
 
+/*!
+******************************************************************************
+       @Function       RA_GetNextLiveSegment
+
+       @Description    Returns details of the next live resource segments
+
+       @Input          pArena - the arena the segment was originally allocated from.
+       @InOut          psSegDetails - rtn details of segments
+
+       @Return         IMG_TRUE if operation succeeded
+******************************************************************************/
 IMG_BOOL RA_GetNextLiveSegment(IMG_HANDLE hArena, RA_SEGMENT_DETAILS *psSegDetails)
 {
        BT        *pBT;
@@ -1400,7 +1796,7 @@ IMG_BOOL RA_GetNextLiveSegment(IMG_HANDLE hArena, RA_SEGMENT_DETAILS *psSegDetai
 
                pBT = pArena->pHeadSegment;
        }
-       
+       /* walk the arena segments and write live one to the  buffer */
        while (pBT != IMG_NULL)
        {
                if (pBT->type == btt_live)
@@ -1479,9 +1875,19 @@ _BTType (IMG_INT eType)
        }
        return "junk";
 }
-#endif 
+#endif /*defined(CONFIG_PROC_FS) && defined(DEBUG)*/
 
 #if defined(ENABLE_RA_DUMP)
+/*!
+******************************************************************************
+       @Function       RA_Dump
+
+       @Description    To dump a readable description of an arena. Diagnostic only.
+
+       @Input          pArena - the arena to dump.
+
+       @Return         None
+******************************************************************************/
 IMG_VOID
 RA_Dump (RA_ARENA *pArena)
 {
@@ -1501,16 +1907,15 @@ RA_Dump (RA_ARENA *pArena)
 
        for (pBT=pArena->pHeadSegment; pBT!=IMG_NULL; pBT=pBT->pNextSegment)
        {
-               PVR_DPF ((PVR_DBG_MESSAGE,"\tbase=0x%x size=0x%x type=%s ref=%08X",
-                                (IMG_UINT32) pBT->base, pBT->uSize, _BTType (pBT->type),
-                                pBT->pRef));
+               PVR_DPF ((PVR_DBG_MESSAGE,"\tbase=0x%x size=0x%x type=%s",
+                                (IMG_UINT32) pBT->base, pBT->uSize, _BTType (pBT->type)));
        }
 
 #ifdef HASH_TRACE
        HASH_Dump (pArena->pSegmentHash);
 #endif
 }
-#endif 
+#endif /* #if defined(ENABLE_RA_DUMP) */
 
 
 #if defined(CONFIG_PROC_FS) && defined(DEBUG)
@@ -1607,10 +2012,22 @@ static void* RA_ProcSeqOff2ElementRegs(struct seq_file * sfile, loff_t off)
        return (void*)pBT;
 }
 
-#endif 
+#endif /* defined(CONFIG_PROC_FS) && defined(DEBUG) */
 
 
 #ifdef RA_STATS
+/*!
+******************************************************************************
+       @Function       RA_GetStats
+
+       @Description    Gets the arena stats and places in client buffer
+
+       @Input          pArena - the arena to print statistics for.
+       @Input          ppszStr - caller string to fill
+       @Input          pui32StrLen - length of caller string
+
+       @Return         PVRSRV_ERROR
+******************************************************************************/
 PVRSRV_ERROR RA_GetStats(RA_ARENA *pArena,
                                                        IMG_CHAR **ppszStr,
                                                        IMG_UINT32 *pui32StrLen)
@@ -1723,3 +2140,10 @@ PVRSRV_ERROR RA_GetStatsFreeMem(RA_ARENA *pArena,
 }
 #endif
 
+/******************************************************************************
+ End of file (ra.c)
+******************************************************************************/
+
+
+
+
diff --git a/services4/srvkm/common/refcount.c b/services4/srvkm/common/refcount.c
new file mode 100644 (file)
index 0000000..fa64b23
--- /dev/null
@@ -0,0 +1,588 @@
+/*************************************************************************/ /*!
+@Title          Services reference count debugging
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+#if defined(PVRSRV_REFCOUNT_DEBUG)
+
+#include "services_headers.h"
+
+#ifndef __linux__
+#warning Reference count debugging is not thread-safe on this platform
+#define PVRSRV_LOCK_CCB()
+#define PVRSRV_UNLOCK_CCB()
+#else /* __linux__ */
+#include <linux/spinlock.h>
+static DEFINE_SPINLOCK(gsCCBLock);
+#define PVRSRV_LOCK_CCB() \
+       { \
+               unsigned long flags; \
+               spin_lock_irqsave(&gsCCBLock, flags);
+#define PVRSRV_UNLOCK_CCB()    \
+               spin_unlock_irqrestore(&gsCCBLock, flags); \
+       }
+#endif /* __linux__ */
+
+#define PVRSRV_REFCOUNT_CCB_MAX                        512
+#define PVRSRV_REFCOUNT_CCB_MESG_MAX   80
+
+#define PVRSRV_REFCOUNT_CCB_DEBUG_SYNCINFO     (1U << 0)
+#define PVRSRV_REFCOUNT_CCB_DEBUG_MEMINFO      (1U << 1)
+#define PVRSRV_REFCOUNT_CCB_DEBUG_BM_BUF       (1U << 2)
+#define PVRSRV_REFCOUNT_CCB_DEBUG_BM_BUF2      (1U << 3)
+#define PVRSRV_REFCOUNT_CCB_DEBUG_BM_XPROC     (1U << 4)
+
+#if defined(__linux__)
+#define PVRSRV_REFCOUNT_CCB_DEBUG_MMAP         (1U << 16)
+#define PVRSRV_REFCOUNT_CCB_DEBUG_MMAP2                (1U << 17)
+#else
+#define PVRSRV_REFCOUNT_CCB_DEBUG_MMAP         0
+#define PVRSRV_REFCOUNT_CCB_DEBUG_MMAP2                0
+#endif
+
+#define PVRSRV_REFCOUNT_CCB_DEBUG_ALL          ~0U
+
+/*static const IMG_UINT guiDebugMask = PVRSRV_REFCOUNT_CCB_DEBUG_ALL;*/
+static const IMG_UINT guiDebugMask =
+       PVRSRV_REFCOUNT_CCB_DEBUG_SYNCINFO |
+       PVRSRV_REFCOUNT_CCB_DEBUG_MMAP2;
+
+typedef struct
+{
+       const IMG_CHAR *pszFile;
+       IMG_INT iLine;
+       IMG_UINT32 ui32PID;
+       IMG_CHAR pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX];
+}
+PVRSRV_REFCOUNT_CCB;
+
+static PVRSRV_REFCOUNT_CCB gsRefCountCCB[PVRSRV_REFCOUNT_CCB_MAX];
+static IMG_UINT giOffset;
+
+static const IMG_CHAR gszHeader[] =
+       /*        10        20        30        40        50        60        70
+        * 345678901234567890123456789012345678901234567890123456789012345678901
+        */
+       "TYPE     SYNCINFO MEMINFO  MEMHANDLE OTHER    REF  REF' SIZE     PID";
+       /* NCINFO deadbeef deadbeef deadbeef  deadbeef 1234 1234 deadbeef */
+
+#define PVRSRV_REFCOUNT_CCB_FMT_STRING "%8.8s %8p %8p %8p  %8p %.4d %.4d %.8x"
+
+IMG_INTERNAL
+void PVRSRVDumpRefCountCCB(void)
+{
+       int i;
+
+       PVRSRV_LOCK_CCB();
+
+       PVR_LOG(("%s", gszHeader));
+
+       for(i = 0; i < PVRSRV_REFCOUNT_CCB_MAX; i++)
+       {
+               PVRSRV_REFCOUNT_CCB *psRefCountCCBEntry =
+                       &gsRefCountCCB[(giOffset + i) % PVRSRV_REFCOUNT_CCB_MAX];
+
+               /* Early on, we won't have MAX_REFCOUNT_CCB_SIZE messages */
+               if(!psRefCountCCBEntry->pszFile)
+                       break;
+
+               PVR_LOG(("%s %d %s:%d", psRefCountCCBEntry->pcMesg,
+                                                               psRefCountCCBEntry->ui32PID,
+                                                               psRefCountCCBEntry->pszFile,
+                                                               psRefCountCCBEntry->iLine));
+       }
+
+       PVRSRV_UNLOCK_CCB();
+}
+
+IMG_INTERNAL
+void PVRSRVKernelSyncInfoIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                                PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo,
+                                                                PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       IMG_UINT32 ui32RefValue = OSAtomicRead(psKernelSyncInfo->pvRefCount);
+
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_SYNCINFO))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "SYNCINFO",
+                        psKernelSyncInfo,
+                        psKernelMemInfo,
+                        NULL,
+                        (psKernelMemInfo) ? psKernelMemInfo->sMemBlk.hOSMemHandle : NULL,
+                        ui32RefValue,
+                        ui32RefValue + 1,
+                        (psKernelMemInfo) ? psKernelMemInfo->uAllocSize : 0);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       PVRSRVAcquireSyncInfoKM(psKernelSyncInfo);
+}
+
+IMG_INTERNAL
+void PVRSRVKernelSyncInfoDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                                PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo,
+                                                                PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       IMG_UINT32 ui32RefValue = OSAtomicRead(psKernelSyncInfo->pvRefCount);
+
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_SYNCINFO))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "SYNCINFO",
+                        psKernelSyncInfo,
+                        psKernelMemInfo,
+                        (psKernelMemInfo) ? psKernelMemInfo->sMemBlk.hOSMemHandle : NULL,
+                        NULL,
+                        ui32RefValue,
+                        ui32RefValue - 1,
+                        (psKernelMemInfo) ? psKernelMemInfo->uAllocSize : 0);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       PVRSRVReleaseSyncInfoKM(psKernelSyncInfo);
+}
+
+IMG_INTERNAL
+void PVRSRVKernelMemInfoIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_MEMINFO))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "MEMINFO",
+                        psKernelMemInfo->psKernelSyncInfo,
+                        psKernelMemInfo,
+                        psKernelMemInfo->sMemBlk.hOSMemHandle,
+                        NULL,
+                        psKernelMemInfo->ui32RefCount,
+                        psKernelMemInfo->ui32RefCount + 1,
+                        psKernelMemInfo->uAllocSize);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       psKernelMemInfo->ui32RefCount++;
+}
+
+IMG_INTERNAL
+void PVRSRVKernelMemInfoDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_MEMINFO))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "MEMINFO",
+                        psKernelMemInfo->psKernelSyncInfo,
+                        psKernelMemInfo,
+                        psKernelMemInfo->sMemBlk.hOSMemHandle,
+                        NULL,
+                        psKernelMemInfo->ui32RefCount,
+                        psKernelMemInfo->ui32RefCount - 1,
+                        psKernelMemInfo->uAllocSize);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       psKernelMemInfo->ui32RefCount--;
+}
+
+IMG_INTERNAL
+void PVRSRVBMBufIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine, BM_BUF *pBuf)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_BM_BUF))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "BM_BUF",
+                        NULL,
+                        NULL,
+                        BM_HandleToOSMemHandle(pBuf),
+                        pBuf,
+                        pBuf->ui32RefCount,
+                        pBuf->ui32RefCount + 1,
+                        (pBuf->pMapping) ? pBuf->pMapping->uSize : 0);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       pBuf->ui32RefCount++;
+}
+
+IMG_INTERNAL
+void PVRSRVBMBufDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine, BM_BUF *pBuf)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_BM_BUF))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "BM_BUF",
+                        NULL,
+                        NULL,
+                        BM_HandleToOSMemHandle(pBuf),
+                        pBuf,
+                        pBuf->ui32RefCount,
+                        pBuf->ui32RefCount - 1,
+                        (pBuf->pMapping) ? pBuf->pMapping->uSize : 0);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       pBuf->ui32RefCount--;
+}
+
+IMG_INTERNAL
+void PVRSRVBMBufIncExport2(const IMG_CHAR *pszFile, IMG_INT iLine, BM_BUF *pBuf)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_BM_BUF2))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "BM_BUF2",
+                        NULL,
+                        NULL,
+                        BM_HandleToOSMemHandle(pBuf),
+                        pBuf,
+                        pBuf->ui32ExportCount,
+                        pBuf->ui32ExportCount + 1,
+                        (pBuf->pMapping) ? pBuf->pMapping->uSize : 0);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       pBuf->ui32ExportCount++;
+}
+
+IMG_INTERNAL
+void PVRSRVBMBufDecExport2(const IMG_CHAR *pszFile, IMG_INT iLine, BM_BUF *pBuf)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_BM_BUF2))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "BM_BUF2",
+                        NULL,
+                        NULL,
+                        BM_HandleToOSMemHandle(pBuf),
+                        pBuf,
+                        pBuf->ui32ExportCount,
+                        pBuf->ui32ExportCount - 1,
+                        (pBuf->pMapping) ? pBuf->pMapping->uSize : 0);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       pBuf->ui32ExportCount--;
+}
+
+IMG_INTERNAL
+void PVRSRVBMXProcIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine, IMG_UINT32 ui32Index)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_BM_XPROC))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "BM_XPROC",
+                        NULL,
+                        NULL,
+                        gXProcWorkaroundShareData[ui32Index].hOSMemHandle,
+                        (IMG_VOID *) ui32Index,
+                        gXProcWorkaroundShareData[ui32Index].ui32RefCount,
+                        gXProcWorkaroundShareData[ui32Index].ui32RefCount + 1,
+                        gXProcWorkaroundShareData[ui32Index].ui32Size);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       gXProcWorkaroundShareData[ui32Index].ui32RefCount++;
+}
+
+IMG_INTERNAL
+void PVRSRVBMXProcDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine, IMG_UINT32 ui32Index)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_BM_XPROC))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "BM_XPROC",
+                        NULL,
+                        NULL,
+                        gXProcWorkaroundShareData[ui32Index].hOSMemHandle,
+                        (IMG_VOID *) ui32Index,
+                        gXProcWorkaroundShareData[ui32Index].ui32RefCount,
+                        gXProcWorkaroundShareData[ui32Index].ui32RefCount - 1,
+                        gXProcWorkaroundShareData[ui32Index].ui32Size);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       gXProcWorkaroundShareData[ui32Index].ui32RefCount--;
+}
+
+#if defined(__linux__)
+
+/* mmap refcounting is Linux specific */
+
+IMG_INTERNAL
+void PVRSRVOffsetStructIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                          PKV_OFFSET_STRUCT psOffsetStruct)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_MMAP))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "MMAP",
+                        NULL,
+                        NULL,
+                        psOffsetStruct->psLinuxMemArea,
+                        psOffsetStruct,
+                        psOffsetStruct->ui32RefCount,
+                        psOffsetStruct->ui32RefCount + 1,
+                        psOffsetStruct->ui32RealByteSize);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       psOffsetStruct->ui32RefCount++;
+}
+
+IMG_INTERNAL
+void PVRSRVOffsetStructDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                          PKV_OFFSET_STRUCT psOffsetStruct)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_MMAP))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "MMAP",
+                        NULL,
+                        NULL,
+                        psOffsetStruct->psLinuxMemArea,
+                        psOffsetStruct,
+                        psOffsetStruct->ui32RefCount,
+                        psOffsetStruct->ui32RefCount - 1,
+                        psOffsetStruct->ui32RealByteSize);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       psOffsetStruct->ui32RefCount--;
+}
+
+IMG_INTERNAL
+void PVRSRVOffsetStructIncMapped2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                                 PKV_OFFSET_STRUCT psOffsetStruct)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_MMAP2))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "MMAP2",
+                        NULL,
+                        NULL,
+                        psOffsetStruct->psLinuxMemArea,
+                        psOffsetStruct,
+                        psOffsetStruct->ui32Mapped,
+                        psOffsetStruct->ui32Mapped + 1,
+                        psOffsetStruct->ui32RealByteSize);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       psOffsetStruct->ui32Mapped++;
+}
+
+IMG_INTERNAL
+void PVRSRVOffsetStructDecMapped2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                                 PKV_OFFSET_STRUCT psOffsetStruct)
+{
+       if(!(guiDebugMask & PVRSRV_REFCOUNT_CCB_DEBUG_MMAP2))
+               goto skip;
+
+       PVRSRV_LOCK_CCB();
+
+       gsRefCountCCB[giOffset].pszFile = pszFile;
+       gsRefCountCCB[giOffset].iLine = iLine;
+       gsRefCountCCB[giOffset].ui32PID = OSGetCurrentProcessIDKM();
+       snprintf(gsRefCountCCB[giOffset].pcMesg,
+                        PVRSRV_REFCOUNT_CCB_MESG_MAX - 1,
+                        PVRSRV_REFCOUNT_CCB_FMT_STRING,
+                        "MMAP2",
+                        NULL,
+                        NULL,
+                        psOffsetStruct->psLinuxMemArea,
+                        psOffsetStruct,
+                        psOffsetStruct->ui32Mapped,
+                        psOffsetStruct->ui32Mapped - 1,
+                        psOffsetStruct->ui32RealByteSize);
+       gsRefCountCCB[giOffset].pcMesg[PVRSRV_REFCOUNT_CCB_MESG_MAX - 1] = 0;
+       giOffset = (giOffset + 1) % PVRSRV_REFCOUNT_CCB_MAX;
+
+       PVRSRV_UNLOCK_CCB();
+
+skip:
+       psOffsetStruct->ui32Mapped--;
+}
+
+#endif /* defined(__linux__) */
+
+#endif /* defined(PVRSRV_REFCOUNT_DEBUG) */
index 5088c7f..aef102f 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Resource Manager
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provide resource management
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #include "services_headers.h"
 #include "resman.h"
 
@@ -81,49 +96,56 @@ static DECLARE_MUTEX(lock);
 
 #define RESMAN_SIGNATURE 0x12345678
 
+/******************************************************************************
+ * resman structures
+ *****************************************************************************/
+
+/* resman item structure */
 typedef struct _RESMAN_ITEM_
 {
 #ifdef DEBUG
        IMG_UINT32                              ui32Signature;
 #endif
-       struct _RESMAN_ITEM_    **ppsThis;      
-       struct _RESMAN_ITEM_    *psNext;        
+       struct _RESMAN_ITEM_    **ppsThis;      /*!< list navigation */
+       struct _RESMAN_ITEM_    *psNext;        /*!< list navigation */
 
-       IMG_UINT32                              ui32Flags;      
-       IMG_UINT32                              ui32ResType;
+       IMG_UINT32                              ui32Flags;      /*!< flags */
+       IMG_UINT32                              ui32ResType;/*!< res type */
 
-       IMG_PVOID                               pvParam;        
-       IMG_UINT32                              ui32Param;      
+       IMG_PVOID                               pvParam;        /*!< param1 for callback */
+       IMG_UINT32                              ui32Param;      /*!< param2 for callback */
 
-       RESMAN_FREE_FN                  pfnFreeResource;
+       RESMAN_FREE_FN                  pfnFreeResource;/*!< resman item free callback */
 } RESMAN_ITEM;
 
 
+/* resman context structure */
 typedef struct _RESMAN_CONTEXT_
 {
 #ifdef DEBUG
        IMG_UINT32                                      ui32Signature;
 #endif
-       struct  _RESMAN_CONTEXT_        **ppsThis;
-       struct  _RESMAN_CONTEXT_        *psNext;
+       struct  _RESMAN_CONTEXT_        **ppsThis;/*!< list navigation */
+       struct  _RESMAN_CONTEXT_        *psNext;/*!< list navigation */
 
-       PVRSRV_PER_PROCESS_DATA         *psPerProc; 
+       PVRSRV_PER_PROCESS_DATA         *psPerProc; /* owner of resources */
 
-       RESMAN_ITEM                                     *psResItemList;
+       RESMAN_ITEM                                     *psResItemList;/*!< res item list for context */
 
 } RESMAN_CONTEXT;
 
 
+/* resman list structure */
 typedef struct
 {
-       RESMAN_CONTEXT  *psContextList; 
+       RESMAN_CONTEXT  *psContextList; /*!< resman context list */
 
-} RESMAN_LIST, *PRESMAN_LIST;  
+} RESMAN_LIST, *PRESMAN_LIST;  /* PRQA S 3205 */
 
 
 PRESMAN_LIST   gpsResList = IMG_NULL;
 
-#include "lists.h"      
+#include "lists.h"     /* PRQA S 5087 */ /* include lists.h required here */
 
 static IMPLEMENT_LIST_ANY_VA(RESMAN_ITEM)
 static IMPLEMENT_LIST_ANY_VA_2(RESMAN_ITEM, IMG_BOOL, IMG_FALSE)
@@ -137,6 +159,8 @@ static IMPLEMENT_LIST_INSERT(RESMAN_CONTEXT)
 
 #define PRINT_RESLIST(x, y, z)
 
+/******************************************************** Forword references */
+
 static PVRSRV_ERROR FreeResourceByPtr(RESMAN_ITEM *psItem, IMG_BOOL bExecuteCallback, IMG_BOOL bForceCleanup);
 
 static PVRSRV_ERROR FreeResourceByCriteria(PRESMAN_CONTEXT     psContext,
@@ -159,11 +183,21 @@ static PVRSRV_ERROR FreeResourceByCriteria(PRESMAN_CONTEXT        psContext,
 
 
 
+/*!
+******************************************************************************
+
+ @Function     ResManInit
+
+ @Description initialises the resman
+
+ @Return   none
+
+******************************************************************************/
 PVRSRV_ERROR ResManInit(IMG_VOID)
 {
        if (gpsResList == IMG_NULL)
        {
-               
+               /* If not already initialised */
                if (OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                                sizeof(*gpsResList),
                                                (IMG_VOID **)&gpsResList, IMG_NULL,
@@ -172,10 +206,10 @@ PVRSRV_ERROR ResManInit(IMG_VOID)
                        return PVRSRV_ERROR_OUT_OF_MEMORY;
                }
 
-               
+               /* Init list, the linked list has dummy entries at both ends */
                gpsResList->psContextList = IMG_NULL;
 
-               
+               /* Check resource list */
                VALIDATERESLIST();
        }
 
@@ -183,30 +217,52 @@ PVRSRV_ERROR ResManInit(IMG_VOID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     ResManDeInit
+
+ @Description de-initialises the resman
+
+ @Return   none
+
+******************************************************************************/
 IMG_VOID ResManDeInit(IMG_VOID)
 {
        if (gpsResList != IMG_NULL)
        {
-               
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(*gpsResList), gpsResList, IMG_NULL);
                gpsResList = IMG_NULL;
        }
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVResManConnect
+
+ @Description Opens a connection to the Resource Manager
+
+ @input        hPerProc - Per-process data (if applicable)
+ @output       phResManContext - Resman context
+
+ @Return    error code or PVRSRV_OK
+
+******************************************************************************/
 PVRSRV_ERROR PVRSRVResManConnect(IMG_HANDLE                    hPerProc,
                                                                 PRESMAN_CONTEXT        *phResManContext)
 {
        PVRSRV_ERROR    eError;
        PRESMAN_CONTEXT psResManContext;
 
-       
+       /*Acquire resource list sync object*/
        ACQUIRE_SYNC_OBJ;
 
-       
+       /*Check resource list*/
        VALIDATERESLIST();
 
-       
+       /* Allocate memory for the new context. */
        eError = OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(*psResManContext),
                                                (IMG_VOID **)&psResManContext, IMG_NULL,
                                                "Resource Manager Context");
@@ -214,10 +270,10 @@ PVRSRV_ERROR PVRSRVResManConnect(IMG_HANDLE                       hPerProc,
        {
                PVR_DPF((PVR_DBG_ERROR, "PVRSRVResManConnect: ERROR allocating new RESMAN context struct"));
 
-               
+               /* Check resource list */
                VALIDATERESLIST();
 
-               
+               /* Release resource list sync object */
                RELEASE_SYNC_OBJ;
 
                return eError;
@@ -225,17 +281,17 @@ PVRSRV_ERROR PVRSRVResManConnect(IMG_HANDLE                       hPerProc,
 
 #ifdef DEBUG
        psResManContext->ui32Signature = RESMAN_SIGNATURE;
-#endif 
+#endif /* DEBUG */
        psResManContext->psResItemList  = IMG_NULL;
        psResManContext->psPerProc = hPerProc;
 
-       
+       /* Insert new context struct after the dummy first entry */
        List_RESMAN_CONTEXT_Insert(&gpsResList->psContextList, psResManContext);
 
-       
+       /* Check resource list */
        VALIDATERESLIST();
 
-       
+       /* Release resource list sync object */
        RELEASE_SYNC_OBJ;
 
        *phResManContext = psResManContext;
@@ -244,38 +300,51 @@ PVRSRV_ERROR PVRSRVResManConnect(IMG_HANDLE                       hPerProc,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     PVRSRVResManDisconnect
+
+ @Description Closes a Resource Manager connection and frees all resources
+
+ @input        hResManContext - Resman context
+ @input        bKernelContext - IMG_TRUE for kernel contexts
+
+ @Return       IMG_VOID
+
+******************************************************************************/
 IMG_VOID PVRSRVResManDisconnect(PRESMAN_CONTEXT psResManContext,
                                                                IMG_BOOL                bKernelContext)
 {
-       
+       /* Acquire resource list sync object */
        ACQUIRE_SYNC_OBJ;
 
-       
+       /* Check resource list */
        VALIDATERESLIST();
 
-       
+       /* Print and validate resource list */
        PRINT_RESLIST(gpsResList, psResManContext, IMG_TRUE);
 
-       
+       /* Free all auto-freed resources in order */
 
        if (!bKernelContext)
        {
-               
+               /* OS specific User-mode Mappings: */
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_OS_USERMODE_MAPPING, 0, 0, IMG_TRUE);
 
-               
+               /* VGX types: */
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_DMA_CLIENT_FIFO_DATA, 0, 0, IMG_TRUE);
 
-               
+               /* Event Object */
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_EVENT_OBJECT, 0, 0, IMG_TRUE);
 
-               
-               
+               /* syncobject state (Read/Write Complete values) */
+               /* Must be FIFO, so we reverse the list, twice */
                List_RESMAN_ITEM_Reverse(&psResManContext->psResItemList);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_MODIFY_SYNC_OPS, 0, 0, IMG_TRUE);
-               List_RESMAN_ITEM_Reverse(&psResManContext->psResItemList);  
+               List_RESMAN_ITEM_Reverse(&psResManContext->psResItemList);  // (could survive without this - all following items would be cleared up "fifo" too)
 
-               
+               /* SGX types: */
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_HW_RENDER_CONTEXT, 0, 0, IMG_TRUE);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_HW_TRANSFER_CONTEXT, 0, 0, IMG_TRUE);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_HW_2D_CONTEXT, 0, 0, IMG_TRUE);
@@ -283,9 +352,7 @@ IMG_VOID PVRSRVResManDisconnect(PRESMAN_CONTEXT psResManContext,
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_SHARED_PB_DESC_CREATE_LOCK, 0, 0, IMG_TRUE);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_SHARED_PB_DESC, 0, 0, IMG_TRUE);
                
-               
-
-               
+               /* COMMON types: */
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_SYNC_INFO, 0, 0, IMG_TRUE);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_DEVICECLASSMEM_MAPPING, 0, 0, IMG_TRUE);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_DEVICEMEM_WRAP, 0, 0, IMG_TRUE);
@@ -294,37 +361,57 @@ IMG_VOID PVRSRVResManDisconnect(PRESMAN_CONTEXT psResManContext,
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_DEVICEMEM_ALLOCATION, 0, 0, IMG_TRUE);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_DEVICEMEM_CONTEXT, 0, 0, IMG_TRUE);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_SHARED_MEM_INFO, 0, 0, IMG_TRUE);
-
-               
+#if defined(SUPPORT_ION)
+               FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_DEVICEMEM_ION, 0, 0, IMG_TRUE);
+#endif
+               /* DISPLAY CLASS types: */
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_DISPLAYCLASS_SWAPCHAIN_REF, 0, 0, IMG_TRUE);
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_DISPLAYCLASS_DEVICE, 0, 0, IMG_TRUE);
 
-               
+               /* BUFFER CLASS types: */
                FreeResourceByCriteria(psResManContext, RESMAN_CRITERIA_RESTYPE, RESMAN_TYPE_BUFFERCLASS_DEVICE, 0, 0, IMG_TRUE);
        }
 
-       
+       /* Ensure that there are no resources left */
        PVR_ASSERT(psResManContext->psResItemList == IMG_NULL);
 
-       
+       /* Remove the context struct from the list */
        List_RESMAN_CONTEXT_Remove(psResManContext);
 
-       
+       /* Free the context struct */
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(RESMAN_CONTEXT), psResManContext, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
 
-       
+       /* Check resource list */
        VALIDATERESLIST();
 
-       
+       /* Print and validate resource list */
        PRINT_RESLIST(gpsResList, psResManContext, IMG_FALSE);
 
-       
+       /* Release resource list sync object */
        RELEASE_SYNC_OBJ;
 }
 
 
+/*!
+******************************************************************************
+ @Function      ResManRegisterRes
+
+ @Description    : Inform the resource manager that the given resource has
+                                  been alloacted and freeing of it will be the responsibility
+                                  of the resource manager
+
+ @input        psResManContext - resman context
+ @input        ui32ResType - identify what kind of resource it is
+ @input        pvParam - address of resource
+ @input        ui32Param - size of resource
+ @input        pfnFreeResource - pointer to function that frees this resource
+
+ @Return   On success a pointer to an opaque data structure that represents
+                                               the allocated resource, else NULL
+
+**************************************************************************/
 PRESMAN_ITEM ResManRegisterRes(PRESMAN_CONTEXT psResManContext,
                                                           IMG_UINT32           ui32ResType,
                                                           IMG_PVOID            pvParam,
@@ -342,10 +429,10 @@ PRESMAN_ITEM ResManRegisterRes(PRESMAN_CONTEXT    psResManContext,
                return (PRESMAN_ITEM) IMG_NULL;
        }
 
-       
+       /* Acquire resource list sync object */
        ACQUIRE_SYNC_OBJ;
 
-       
+       /* Check resource list */
        VALIDATERESLIST();
 
        PVR_DPF((PVR_DBG_MESSAGE, "ResManRegisterRes: register resource "
@@ -357,7 +444,7 @@ PRESMAN_ITEM ResManRegisterRes(PRESMAN_CONTEXT      psResManContext,
                        ui32Param,
                        (IMG_UINTPTR_T)pfnFreeResource));
 
-       
+       /* Allocate memory for the new resource structure */
        if (OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
                                   sizeof(RESMAN_ITEM), (IMG_VOID **)&psNewResItem,
                                   IMG_NULL,
@@ -366,34 +453,45 @@ PRESMAN_ITEM ResManRegisterRes(PRESMAN_CONTEXT    psResManContext,
                PVR_DPF((PVR_DBG_ERROR, "ResManRegisterRes: "
                                "ERROR allocating new resource item"));
 
-               
+               /* Release resource list sync object */
                RELEASE_SYNC_OBJ;
 
                return((PRESMAN_ITEM)IMG_NULL);
        }
 
-       
+       /* Fill in details about this resource */
 #ifdef DEBUG
        psNewResItem->ui32Signature             = RESMAN_SIGNATURE;
-#endif 
+#endif /* DEBUG */
        psNewResItem->ui32ResType               = ui32ResType;
        psNewResItem->pvParam                   = pvParam;
        psNewResItem->ui32Param                 = ui32Param;
        psNewResItem->pfnFreeResource   = pfnFreeResource;
        psNewResItem->ui32Flags             = 0;
 
-       
+       /* Insert new structure after dummy first entry */
        List_RESMAN_ITEM_Insert(&psResManContext->psResItemList, psNewResItem);
 
-       
+       /* Check resource list */
        VALIDATERESLIST();
 
-       
+       /* Release resource list sync object */
        RELEASE_SYNC_OBJ;
 
        return(psNewResItem);
 }
 
+/*!
+******************************************************************************
+ @Function             ResManFreeResByPtr
+
+ @Description   frees a resource by matching on pointer type
+
+ @inputs        psResItem - pointer to resource item to free
+                bForceCleanup  - ignored uKernel re-sync
+
+ @Return               PVRSRV_ERROR
+**************************************************************************/
 PVRSRV_ERROR ResManFreeResByPtr(RESMAN_ITEM    *psResItem, IMG_BOOL bForceCleanup)
 {
        PVRSRV_ERROR eError;
@@ -409,25 +507,40 @@ PVRSRV_ERROR ResManFreeResByPtr(RESMAN_ITEM       *psResItem, IMG_BOOL bForceCleanup)
        PVR_DPF((PVR_DBG_MESSAGE, "ResManFreeResByPtr: freeing resource at %08X",
                        (IMG_UINTPTR_T)psResItem));
 
-       
+       /*Acquire resource list sync object*/
        ACQUIRE_SYNC_OBJ;
 
-       
+       /*Check resource list*/
        VALIDATERESLIST();
 
-       
+       /*Free resource*/
        eError = FreeResourceByPtr(psResItem, IMG_TRUE, bForceCleanup);
 
-       
+       /*Check resource list*/
        VALIDATERESLIST();
 
-       
+       /*Release resource list sync object*/
        RELEASE_SYNC_OBJ;
 
        return(eError);
 }
 
 
+/*!
+******************************************************************************
+ @Function             ResManFreeResByCriteria
+
+ @Description   frees a resource by matching on criteria
+
+ @inputs               hResManContext - handle for resman context
+ @inputs        ui32SearchCriteria - indicates which parameters should be
+                               used in search for resources to free
+ @inputs        ui32ResType - identify what kind of resource to free
+ @inputs        pvParam - address of resource to be free
+ @inputs        ui32Param - size of resource to be free
+
+ @Return               PVRSRV_ERROR
+**************************************************************************/
 PVRSRV_ERROR ResManFreeResByCriteria(PRESMAN_CONTEXT   psResManContext,
                                                                         IMG_UINT32                     ui32SearchCriteria,
                                                                         IMG_UINT32                     ui32ResType,
@@ -438,10 +551,10 @@ PVRSRV_ERROR ResManFreeResByCriteria(PRESMAN_CONTEXT      psResManContext,
 
        PVR_ASSERT(psResManContext != IMG_NULL);
 
-       
+       /* Acquire resource list sync object */
        ACQUIRE_SYNC_OBJ;
 
-       
+       /* Check resource list */
        VALIDATERESLIST();
 
        PVR_DPF((PVR_DBG_MESSAGE, "ResManFreeResByCriteria: "
@@ -449,21 +562,32 @@ PVRSRV_ERROR ResManFreeResByCriteria(PRESMAN_CONTEXT      psResManContext,
                        (IMG_UINTPTR_T)psResManContext, ui32SearchCriteria, ui32ResType,
                        (IMG_UINTPTR_T)pvParam, ui32Param));
 
-       
+       /* Free resources by criteria for this context */
        eError = FreeResourceByCriteria(psResManContext, ui32SearchCriteria,
                                                                        ui32ResType, pvParam, ui32Param,
                                                                        IMG_TRUE);
 
-       
+       /* Check resource list */
        VALIDATERESLIST();
 
-       
+       /* Release resource list sync object */
        RELEASE_SYNC_OBJ;
 
        return eError;
 }
 
 
+/*!
+******************************************************************************
+ @Function             ResManDissociateRes
+
+ @Description   Moves a resource from one context to another.
+
+ @inputs        psResItem - pointer to resource item to dissociate
+ @inputs               psNewResManContext - new resman context for the resource
+
+ @Return               IMG_VOID
+**************************************************************************/
 PVRSRV_ERROR ResManDissociateRes(RESMAN_ITEM           *psResItem,
                                                         PRESMAN_CONTEXT        psNewResManContext)
 {
@@ -478,16 +602,16 @@ PVRSRV_ERROR ResManDissociateRes(RESMAN_ITEM              *psResItem,
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-#ifdef DEBUG 
+#ifdef DEBUG /* QAC fix */
        PVR_ASSERT(psResItem->ui32Signature == RESMAN_SIGNATURE);
 #endif
 
        if (psNewResManContext != IMG_NULL)
        {
-               
+               /* Remove this item from its old resource list */
                List_RESMAN_ITEM_Remove(psResItem);
 
-               
+               /* Re-insert into new list */
                List_RESMAN_ITEM_Insert(&psNewResManContext->psResItemList, psResItem);
 
        }
@@ -504,6 +628,19 @@ PVRSRV_ERROR ResManDissociateRes(RESMAN_ITEM               *psResItem,
        return eError;
 }
 
+/*!
+******************************************************************************
+ @Function             ResManFindResourceByPtr_AnyVaCb
+
+ @Description
+                                       Compares the resman item with a given pointer.
+
+ @inputs               psCurItem - theThe item to check
+ @inputs        va - Variable argument list with:
+                                        psItem - pointer to resource item to find
+
+ @Return               IMG_BOOL
+**************************************************************************/
 static IMG_BOOL ResManFindResourceByPtr_AnyVaCb(RESMAN_ITEM *psCurItem, va_list va)
 {
        RESMAN_ITEM             *psItem;
@@ -514,9 +651,23 @@ static IMG_BOOL ResManFindResourceByPtr_AnyVaCb(RESMAN_ITEM *psCurItem, va_list
 }
 
 
+/*!
+******************************************************************************
+ @Function             ResManFindResourceByPtr
+
+ @Description
+                                       Attempts to find a resource in the list for this context
+
+ @inputs               hResManContext - handle for resman context
+ @inputs        psItem - pointer to resource item to find
+
+ @Return               PVRSRV_ERROR
+**************************************************************************/
 IMG_INTERNAL PVRSRV_ERROR ResManFindResourceByPtr(PRESMAN_CONTEXT      psResManContext,
                                                                                                  RESMAN_ITEM           *psItem)
 {
+/*     RESMAN_ITEM             *psCurItem;*/
+
        PVRSRV_ERROR    eResult;
 
        PVR_ASSERT(psResManContext != IMG_NULL);
@@ -529,11 +680,11 @@ IMG_INTERNAL PVRSRV_ERROR ResManFindResourceByPtr(PRESMAN_CONTEXT psResManContex
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-#ifdef DEBUG   
+#ifdef DEBUG   /* QAC fix */
        PVR_ASSERT(psItem->ui32Signature == RESMAN_SIGNATURE);
 #endif
 
-       
+       /* Acquire resource list sync object */
        ACQUIRE_SYNC_OBJ;
 
        PVR_DPF((PVR_DBG_MESSAGE,
@@ -550,7 +701,7 @@ IMG_INTERNAL PVRSRV_ERROR ResManFindResourceByPtr(PRESMAN_CONTEXT   psResManContex
                        (IMG_UINTPTR_T)psItem->pfnFreeResource,
                        psItem->ui32Flags));
 
-       
+       /* Search resource items starting at after the first dummy item */
        if(List_RESMAN_ITEM_IMG_BOOL_Any_va(psResManContext->psResItemList,
                                                                                &ResManFindResourceByPtr_AnyVaCb,
                                                                                psItem))
@@ -562,12 +713,28 @@ IMG_INTERNAL PVRSRV_ERROR ResManFindResourceByPtr(PRESMAN_CONTEXT psResManContex
                eResult = PVRSRV_ERROR_NOT_OWNER;
        }
 
-       
+       /* Release resource list sync object */
        RELEASE_SYNC_OBJ;
 
+/*     return PVRSRV_ERROR_NOT_OWNER;*/
        return eResult;
 }
 
+/*!
+******************************************************************************
+ @Function             FreeResourceByPtr
+
+ @Description
+                                       Frees a resource and move it from the list
+                                       NOTE : this function must be called with the resource
+                                       list sync object held
+
+ @inputs        psItem - pointer to resource item to free
+                               bExecuteCallback - execute callback?
+                               bForceCleanup - skips uKernel re-sync
+
+ @Return               PVRSRV_ERROR
+**************************************************************************/
 static PVRSRV_ERROR FreeResourceByPtr(RESMAN_ITEM      *psItem,
                                                                          IMG_BOOL              bExecuteCallback,
                                                                          IMG_BOOL              bForceCleanup)
@@ -582,7 +749,7 @@ static PVRSRV_ERROR FreeResourceByPtr(RESMAN_ITEM   *psItem,
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-#ifdef DEBUG   
+#ifdef DEBUG   /* QAC fix */
        PVR_ASSERT(psItem->ui32Signature == RESMAN_SIGNATURE);
 #endif
 
@@ -597,32 +764,52 @@ static PVRSRV_ERROR FreeResourceByPtr(RESMAN_ITEM *psItem,
                        (IMG_UINTPTR_T)psItem->pvParam, psItem->ui32Param,
                        (IMG_UINTPTR_T)psItem->pfnFreeResource, psItem->ui32Flags));
 
-       
-       List_RESMAN_ITEM_Remove(psItem);
-
-
-       
+       /* Release resource list sync object just in case the free routine calls the resource manager */
        RELEASE_SYNC_OBJ;
 
-       
+       /* Call the freeing routine */
        if (bExecuteCallback)
        {
                eError = psItem->pfnFreeResource(psItem->pvParam, psItem->ui32Param, bForceCleanup);
-               if (eError != PVRSRV_OK)
+               if ((eError != PVRSRV_OK) && (eError != PVRSRV_ERROR_RETRY))
                {
                        PVR_DPF((PVR_DBG_ERROR, "FreeResourceByPtr: ERROR calling FreeResource function"));
                }
        }
 
-       
+       /* Acquire resource list sync object */
        ACQUIRE_SYNC_OBJ;
 
-       
-       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(RESMAN_ITEM), psItem, IMG_NULL);
+       if (eError != PVRSRV_ERROR_RETRY)
+       {
+               /* Remove this item from the resource list */
+               List_RESMAN_ITEM_Remove(psItem);
+
+               /* Free memory for the resource item */
+               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(RESMAN_ITEM), psItem, IMG_NULL);
+       }
 
        return(eError);
 }
 
+/*!
+******************************************************************************
+ @Function             FreeResourceByCriteria_AnyVaCb
+
+ @Description
+                                       Matches a resource manager item with a given criteria.
+
+ @inputs        psCuItem - the item to be matched
+ @inputs               va - a variable argument list with:.
+                                       ui32SearchCriteria - indicates which parameters should be used
+                                       search for resources to free
+                                       ui32ResType - identify what kind of resource to free
+                                       pvParam - address of resource to be free
+                                       ui32Param - size of resource to be free
+
+
+ @Return               psCurItem if matched, IMG_NULL otherwise.
+**************************************************************************/
 static IMG_VOID* FreeResourceByCriteria_AnyVaCb(RESMAN_ITEM *psCurItem, va_list va)
 {
        IMG_UINT32 ui32SearchCriteria;
@@ -635,17 +822,17 @@ static IMG_VOID* FreeResourceByCriteria_AnyVaCb(RESMAN_ITEM *psCurItem, va_list
        pvParam = va_arg(va, IMG_PVOID);
        ui32Param = va_arg(va, IMG_UINT32);
 
-       
+       /*check that for all conditions are either disabled or eval to true*/
        if(
-       
+       /* Check resource type */
                (((ui32SearchCriteria & RESMAN_CRITERIA_RESTYPE) == 0UL) ||
                (psCurItem->ui32ResType == ui32ResType))
        &&
-       
+       /* Check address */
                (((ui32SearchCriteria & RESMAN_CRITERIA_PVOID_PARAM) == 0UL) ||
                         (psCurItem->pvParam == pvParam))
        &&
-       
+       /* Check size */
                (((ui32SearchCriteria & RESMAN_CRITERIA_UI32_PARAM) == 0UL) ||
                         (psCurItem->ui32Param == ui32Param))
                )
@@ -658,6 +845,27 @@ static IMG_VOID* FreeResourceByCriteria_AnyVaCb(RESMAN_ITEM *psCurItem, va_list
        }
 }
 
+/*!
+******************************************************************************
+ @Function             FreeResourceByCriteria
+
+ @Description
+                                       Frees all resources that match the given criteria for the
+                                       context.
+                                       NOTE : this function must be called with the resource
+                                       list sync object held
+
+ @inputs        psResManContext - pointer to resman context
+ @inputs        ui32SearchCriteria - indicates which parameters should be used
+ @inputs        search for resources to free
+ @inputs        ui32ResType - identify what kind of resource to free
+ @inputs        pvParam - address of resource to be free
+ @inputs        ui32Param - size of resource to be free
+ @inputs        ui32AutoFreeLev - auto free level to free
+ @inputs        bExecuteCallback - execute callback?
+
+ @Return               PVRSRV_ERROR
+**************************************************************************/
 static PVRSRV_ERROR FreeResourceByCriteria(PRESMAN_CONTEXT     psResManContext,
                                                                                   IMG_UINT32           ui32SearchCriteria,
                                                                                   IMG_UINT32           ui32ResType,
@@ -668,8 +876,8 @@ static PVRSRV_ERROR FreeResourceByCriteria(PRESMAN_CONTEXT  psResManContext,
        PRESMAN_ITEM    psCurItem;
        PVRSRV_ERROR    eError = PVRSRV_OK;
 
-       
-       
+       /* Search resource items starting at after the first dummy item */
+       /*while we get a match and not an error*/
        while((psCurItem = (PRESMAN_ITEM)
                                List_RESMAN_ITEM_Any_va(psResManContext->psResItemList,
                                                                                &FreeResourceByCriteria_AnyVaCb,
@@ -679,7 +887,19 @@ static PVRSRV_ERROR FreeResourceByCriteria(PRESMAN_CONTEXT psResManContext,
                                                                                ui32Param)) != IMG_NULL
                        && eError == PVRSRV_OK)
        {
-               eError = FreeResourceByPtr(psCurItem, bExecuteCallback, CLEANUP_WITH_POLL);
+               do
+               {
+                       eError = FreeResourceByPtr(psCurItem, bExecuteCallback, CLEANUP_WITH_POLL);
+                       if (eError == PVRSRV_ERROR_RETRY)
+                       {
+                               RELEASE_SYNC_OBJ;
+                               OSReleaseBridgeLock();
+                               /* Give a chance for other threads to come in and SGX to do more work */
+                               OSSleepms(MAX_CLEANUP_TIME_WAIT_US/1000);
+                               OSReacquireBridgeLock();
+                               ACQUIRE_SYNC_OBJ;
+                       }
+               } while (eError == PVRSRV_ERROR_RETRY);
        }
 
        return eError;
@@ -687,12 +907,23 @@ static PVRSRV_ERROR FreeResourceByCriteria(PRESMAN_CONTEXT        psResManContext,
 
 
 #ifdef DEBUG
+/*!
+******************************************************************************
+ @Function             ValidateResList
+
+ @Description
+                                       Walks the resource list check the pointers
+                                       NOTE : this function must be called with the resource
+                                       list sync object held
+
+ @Return               none
+**************************************************************************/
 static IMG_VOID ValidateResList(PRESMAN_LIST psResList)
 {
        PRESMAN_ITEM    psCurItem, *ppsThisItem;
        PRESMAN_CONTEXT psCurContext, *ppsThisContext;
 
-       
+       /* check we're initialised */
        if (psResList == IMG_NULL)
        {
                PVR_DPF((PVR_DBG_MESSAGE, "ValidateResList: resman not initialised yet"));
@@ -702,10 +933,10 @@ static IMG_VOID ValidateResList(PRESMAN_LIST psResList)
        psCurContext = psResList->psContextList;
        ppsThisContext = &psResList->psContextList;
 
-       
+       /* Walk the context list */
        while(psCurContext != IMG_NULL)
        {
-               
+               /* Check current item */
                PVR_ASSERT(psCurContext->ui32Signature == RESMAN_SIGNATURE);
                if (psCurContext->ppsThis != ppsThisContext)
                {
@@ -718,12 +949,12 @@ static IMG_VOID ValidateResList(PRESMAN_LIST psResList)
                        PVR_ASSERT(psCurContext->ppsThis == ppsThisContext);
                }
 
-               
+               /* Walk the list for this context */
                psCurItem = psCurContext->psResItemList;
                ppsThisItem = &psCurContext->psResItemList;
                while(psCurItem != IMG_NULL)
                {
-                       
+                       /* Check current item */
                        PVR_ASSERT(psCurItem->ui32Signature == RESMAN_SIGNATURE);
                        if (psCurItem->ppsThis != ppsThisItem)
                        {
@@ -736,16 +967,19 @@ static IMG_VOID ValidateResList(PRESMAN_LIST psResList)
                                PVR_ASSERT(psCurItem->ppsThis == ppsThisItem);
                        }
 
-                       
+                       /* Move to next item */
                        ppsThisItem = &psCurItem->psNext;
                        psCurItem = psCurItem->psNext;
                }
 
-               
+               /* Move to next context */
                ppsThisContext = &psCurContext->psNext;
                psCurContext = psCurContext->psNext;
        }
 }
-#endif 
+#endif /* DEBUG */
 
 
+/******************************************************************************
+ End of file (resman.c)
+******************************************************************************/
index 22b9ffb..44dc824 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          MMU Management
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Implements basic low level control of MMU.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "sgxdefs.h"
 #include "sgxmmu.h"
 
 #define UINT32_MAX_VALUE       0xFFFFFFFFUL
 
+/*
+       MMU performs device virtual to physical translation.
+       terminology:
+       page directory (PD)
+       pagetable (PT)
+       data page (DP)
+
+       Incoming 32bit Device Virtual Addresses are deconstructed into 3 fields:
+       ---------------------------------------------------------
+       |       PD Index/tag:   |       PT Index:       |       DP offset:              |
+       |       bits 31:22              |       bits 21:n       |       bits (n-1):0    |
+       ---------------------------------------------------------
+               where typically n=12 for a standard 4k DP
+               but n=16 for a 64k DP
+
+       MMU page directory (PD), pagetable (PT) and data page (DP) config:
+       PD:
+       - always one page per address space
+       - up to 4k in size to span 4Gb (32bit)
+       - contains up to 1024 32bit entries
+       - entries are indexed by the top 12 bits of an incoming 32bit device virtual address
+       - the PD entry selected contains the physical address of the PT to
+         perform the next stage of the V to P translation
+
+       PT:
+       - size depends on the DP size, e.g. 4k DPs have 4k PTs but 16k DPs have 1k PTs
+       - each PT always spans 4Mb of device virtual address space irrespective of DP size
+       - number of entries in a PT depend on DP size and ranges from 1024 to 4 entries
+       - entries are indexed by the PT Index field of the device virtual address (21:n)
+       - the PT entry selected contains the physical address of the DP to access
+
+       DP:
+       - size varies from 4k to 4M in multiple of 4 steppings
+       - DP offset field of the device virtual address ((n-1):0) is used as a byte offset
+         to address into the DP itself
+*/
+
 #define SGX_MAX_PD_ENTRIES     (1<<(SGX_FEATURE_ADDRESS_SPACE_SIZE - SGX_MMU_PT_SHIFT - SGX_MMU_PAGE_SHIFT))
 
 #if defined(FIX_HW_BRN_31620)
-#define SGX_MMU_PDE_DUMMY_PAGE         (0)
-#define SGX_MMU_PTE_DUMMY_PAGE         (0)
+/* Sim doesn't use the address mask */
+#define SGX_MMU_PDE_DUMMY_PAGE         (0)//(0x00000020U)
+#define SGX_MMU_PTE_DUMMY_PAGE         (0)//(0x00000020U)
 
+/* 4MB adress range per page table */
 #define BRN31620_PT_ADDRESS_RANGE_SHIFT                22
 #define BRN31620_PT_ADDRESS_RANGE_SIZE         (1 << BRN31620_PT_ADDRESS_RANGE_SHIFT)
 
+/* 64MB address range per PDE cache line */
 #define BRN31620_PDE_CACHE_FILL_SHIFT          26
 #define BRN31620_PDE_CACHE_FILL_SIZE           (1 << BRN31620_PDE_CACHE_FILL_SHIFT)
 #define BRN31620_PDE_CACHE_FILL_MASK           (BRN31620_PDE_CACHE_FILL_SIZE - 1)
 
+/* Page Directory Enteries per cache line */
 #define BRN31620_PDES_PER_CACHE_LINE_SHIFT     (BRN31620_PDE_CACHE_FILL_SHIFT - BRN31620_PT_ADDRESS_RANGE_SHIFT)
 #define BRN31620_PDES_PER_CACHE_LINE_SIZE      (1 << BRN31620_PDES_PER_CACHE_LINE_SHIFT)
 #define BRN31620_PDES_PER_CACHE_LINE_MASK      (BRN31620_PDES_PER_CACHE_LINE_SIZE - 1)
 
+/* Macros for working out offset for dummy pages */
 #define BRN31620_DUMMY_PAGE_OFFSET     (1 * SGX_MMU_PAGE_SIZE)
 #define BRN31620_DUMMY_PDE_INDEX       (BRN31620_DUMMY_PAGE_OFFSET / BRN31620_PT_ADDRESS_RANGE_SIZE)
 #define BRN31620_DUMMY_PTE_INDEX       ((BRN31620_DUMMY_PAGE_OFFSET - (BRN31620_DUMMY_PDE_INDEX * BRN31620_PT_ADDRESS_RANGE_SIZE))/SGX_MMU_PAGE_SIZE)
 
+/* Cache number of cache lines */
 #define BRN31620_CACHE_FLUSH_SHIFT             (32 - BRN31620_PDE_CACHE_FILL_SHIFT)
 #define BRN31620_CACHE_FLUSH_SIZE              (1 << BRN31620_CACHE_FLUSH_SHIFT)
 
+/* Cache line bits in a UINT32 */
 #define BRN31620_CACHE_FLUSH_BITS_SHIFT                5
 #define BRN31620_CACHE_FLUSH_BITS_SIZE         (1 << BRN31620_CACHE_FLUSH_BITS_SHIFT)
 #define BRN31620_CACHE_FLUSH_BITS_MASK         (BRN31620_CACHE_FLUSH_BITS_SIZE - 1)
 
+/* Cache line index in array */
 #define BRN31620_CACHE_FLUSH_INDEX_BITS                (BRN31620_CACHE_FLUSH_SHIFT - BRN31620_CACHE_FLUSH_BITS_SHIFT)
 #define BRN31620_CACHE_FLUSH_INDEX_SIZE                (1 << BRN31620_CACHE_FLUSH_INDEX_BITS)
 
 
 typedef struct _MMU_PT_INFO_
 {
-       
+       /* note: may need a union here to accommodate a PT page address for local memory */
        IMG_VOID *hPTPageOSMemHandle;
        IMG_CPU_VIRTADDR PTPageCpuVAddr;
-       
-       
+       /* Map of reserved PTEs.
+        * Reserved PTEs are like "valid" PTEs in that they (and the DevVAddrs they represent)
+        * cannot be assigned to another allocation but their "reserved" status persists through
+        * any amount of mapping and unmapping, until the allocation is finally destroyed.
+        *
+        * Reserved and Valid are independent.
+        * When a PTE is first reserved, it will have Reserved=1 and Valid=0.
+        * When the PTE is actually mapped, it will have Reserved=1 and Valid=1.
+        * When the PTE is unmapped, it will have Reserved=1 and Valid=0.
+        * At this point, the PT will can not be destroyed because although there is
+        * not an active mapping on the PT, it is known a PTE is reserved for use.
+        *
+        * The above sequence of mapping and unmapping may repeat any number of times
+        * until the allocation is unmapped and destroyed which causes the PTE to have
+        * Valid=0 and Reserved=0.
+        */
+       /* Number of PTEs set up.
+        * i.e. have a valid SGX Phys Addr and the "VALID" PTE bit == 1
+        */
        IMG_UINT32 ui32ValidPTECount;
 } MMU_PT_INFO;
 
+#define MMU_CONTEXT_NAME_SIZE  50
 struct _MMU_CONTEXT_
 {
-       
+       /* the device node */
        PVRSRV_DEVICE_NODE *psDeviceNode;
 
-       
+       /* Page Directory CPUVirt and DevPhys Addresses */
        IMG_CPU_VIRTADDR pvPDCpuVAddr;
        IMG_DEV_PHYADDR sPDDevPAddr;
 
        IMG_VOID *hPDOSMemHandle;
 
-       
+       /* information about dynamically allocated pagetables */
        MMU_PT_INFO *apsPTInfoList[SGX_MAX_PD_ENTRIES];
 
        PVRSRV_SGXDEV_INFO *psDevInfo;
@@ -108,6 +187,9 @@ struct _MMU_CONTEXT_
 #endif
 #endif
 
+       IMG_UINT32 ui32PID;
+       IMG_CHAR szName[MMU_CONTEXT_NAME_SIZE];
+
 #if defined (FIX_HW_BRN_31620)
        IMG_UINT32 ui32PDChangeMask[BRN31620_CACHE_FLUSH_INDEX_SIZE];
        IMG_UINT32 ui32PDCacheRangeRefCount[BRN31620_CACHE_FLUSH_SIZE];
@@ -118,57 +200,65 @@ struct _MMU_CONTEXT_
 
 struct _MMU_HEAP_
 {
-       
+       /* MMU context */
        MMU_CONTEXT                     *psMMUContext;
 
-       
-
-       
+       /*
+               heap specific details:
+       */
+       /* the Base PD index for the heap */
        IMG_UINT32                      ui32PDBaseIndex;
-       
+       /* number of pagetables in this heap */
        IMG_UINT32                      ui32PageTableCount;
-       
+       /* total number of pagetable entries in this heap which may be mapped to data pages */
        IMG_UINT32                      ui32PTETotalUsable;
-       
+       /* PD entry DP size control field */
        IMG_UINT32                      ui32PDEPageSizeCtrl;
 
-       
-
-       
+       /*
+               Data Page (DP) Details:
+       */
+       /* size in bytes of a data page */
        IMG_UINT32                      ui32DataPageSize;
-       
+       /* bit width of the data page offset addressing field */
        IMG_UINT32                      ui32DataPageBitWidth;
-       
+       /* bit mask of the data page offset addressing field */
        IMG_UINT32                      ui32DataPageMask;
 
-       
-
-       
+       /*
+               PageTable (PT) Details:
+       */
+       /* bit shift to base of PT addressing field */
        IMG_UINT32                      ui32PTShift;
-       
+       /* bit width of the PT addressing field */
        IMG_UINT32                      ui32PTBitWidth;
-       
+       /* bit mask of the PT addressing field */
        IMG_UINT32                      ui32PTMask;
-       
+       /* size in bytes of a pagetable */
        IMG_UINT32                      ui32PTSize;
-       
+       /* Allocated PT Entries per PT */
        IMG_UINT32                      ui32PTNumEntriesAllocated;
-       
+       /* Usable PT Entries per PT (may be different to num allocated for 4MB data page) */
        IMG_UINT32                      ui32PTNumEntriesUsable;
 
-       
-
-       
+       /*
+               PageDirectory Details:
+       */
+       /* bit shift to base of PD addressing field */
        IMG_UINT32                      ui32PDShift;
-       
+       /* bit width of the PD addressing field */
        IMG_UINT32                      ui32PDBitWidth;
-       
+       /* bit mask of the PT addressing field */
        IMG_UINT32                      ui32PDMask;
 
-       
-
+       /*
+               Arena Info:
+       */
        RA_ARENA *psVMArena;
        DEV_ARENA_DESCRIPTOR *psDevArena;
+
+       /* If we have sparse mappings then we can't do PT level sanity checks */
+       IMG_BOOL bHasSparseMappings;
 #if defined(PDUMP)
        PDUMP_MMU_ATTRIB sMMUAttrib;
 #endif
@@ -180,6 +270,7 @@ struct _MMU_HEAP_
 #define DUMMY_DATA_PAGE_SIGNATURE      0xDEADBEEF
 #endif
 
+/* local prototypes: */
 static IMG_VOID
 _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOSFreePT);
 
@@ -190,61 +281,232 @@ MMU_PDumpPageTables      (MMU_HEAP *pMMUHeap,
                                         IMG_SIZE_T uSize,
                                         IMG_BOOL bForUnmap,
                                         IMG_HANDLE hUniqueTag);
-#endif 
+#endif /* #if defined(PDUMP) */
 
+/* This option tests page table memory, for use during device bring-up. */
 #define PAGE_TEST                                      0
 #if PAGE_TEST
 static IMG_VOID PageTest(IMG_VOID* pMem, IMG_DEV_PHYADDR sDevPAddr);
 #endif
 
+/* This option dumps out the PT if an assert fails */
+#define PT_DUMP 1
+
+/* This option sanity checks page table PTE valid count matches active PTEs */
 #define PT_DEBUG 0
-#if PT_DEBUG
+#if (PT_DEBUG || PT_DUMP) && defined(PVRSRV_NEED_PVR_DPF)
 static IMG_VOID DumpPT(MMU_PT_INFO *psPTInfoList)
 {
        IMG_UINT32 *p = (IMG_UINT32*)psPTInfoList->PTPageCpuVAddr;
        IMG_UINT32 i;
 
-       
+       /* 1024 entries in a 4K page table */
        for(i = 0; i < 1024; i += 8)
        {
-               PVR_DPF((PVR_DBG_WARNING,
+               PVR_DPF((PVR_DBG_ERROR,
                                 "%08X %08X %08X %08X %08X %08X %08X %08X\n",
                                 p[i + 0], p[i + 1], p[i + 2], p[i + 3],
                                 p[i + 4], p[i + 5], p[i + 6], p[i + 7]));
        }
 }
+#else /* (PT_DEBUG || PT_DUMP) && defined(PVRSRV_NEED_PVR_DPF) */
+static INLINE IMG_VOID DumpPT(MMU_PT_INFO *psPTInfoList)
+{
+       PVR_UNREFERENCED_PARAMETER(psPTInfoList);
+}
+#endif /* (PT_DEBUG || PT_DUMP) && defined(PVRSRV_NEED_PVR_DPF) */
 
+#if PT_DEBUG
 static IMG_VOID CheckPT(MMU_PT_INFO *psPTInfoList)
 {
        IMG_UINT32 *p = (IMG_UINT32*) psPTInfoList->PTPageCpuVAddr;
        IMG_UINT32 i, ui32Count = 0;
 
-       
+       /* 1024 entries in a 4K page table */
        for(i = 0; i < 1024; i++)
                if(p[i] & SGX_MMU_PTE_VALID)
                        ui32Count++;
 
        if(psPTInfoList->ui32ValidPTECount != ui32Count)
        {
-               PVR_DPF((PVR_DBG_WARNING, "ui32ValidPTECount: %u ui32Count: %u\n",
+               PVR_DPF((PVR_DBG_ERROR, "ui32ValidPTECount: %u ui32Count: %u\n",
                                 psPTInfoList->ui32ValidPTECount, ui32Count));
                DumpPT(psPTInfoList);
                BUG();
        }
 }
-#else 
-static INLINE IMG_VOID DumpPT(MMU_PT_INFO *psPTInfoList)
+#else /* PT_DEBUG */
+static INLINE IMG_VOID CheckPT(MMU_PT_INFO *psPTInfoList)
 {
        PVR_UNREFERENCED_PARAMETER(psPTInfoList);
 }
+#endif /* PT_DEBUG */
 
-static INLINE IMG_VOID CheckPT(MMU_PT_INFO *psPTInfoList)
+/*
+       Debug functionality that allows us to make the CPU
+       mapping of pagetable memory readonly and only make
+       it read/write when we alter it. This allows us
+       to check that our memory isn't being overwritten
+*/
+#if defined(PVRSRV_MMU_MAKE_READWRITE_ON_DEMAND)
+
+#include <linux/version.h>
+
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,38))
+#ifndef AUTOCONF_INCLUDED
+#include <linux/config.h>
+#endif
+#else
+#include <generated/autoconf.h>
+#endif
+
+#include <linux/mm.h>
+#include <linux/sched.h>
+#include <linux/highmem.h>
+#include <asm/pgtable.h>
+#include <asm/tlbflush.h>
+
+static IMG_VOID MakeKernelPageReadWrite(IMG_PVOID ulCPUVAddr)
 {
-       PVR_UNREFERENCED_PARAMETER(psPTInfoList);
+    pgd_t *psPGD;
+    pud_t *psPUD;
+    pmd_t *psPMD;
+    pte_t *psPTE;
+    pte_t ptent;
+    IMG_UINT32 ui32CPUVAddr = (IMG_UINT32) ulCPUVAddr;
+
+    psPGD = pgd_offset_k(ui32CPUVAddr);
+    if (pgd_none(*psPGD) || pgd_bad(*psPGD))
+    {
+        PVR_ASSERT(0);
+    }
+
+    psPUD = pud_offset(psPGD, ui32CPUVAddr);
+    if (pud_none(*psPUD) || pud_bad(*psPUD))
+    {
+        PVR_ASSERT(0);
+    }
+
+    psPMD = pmd_offset(psPUD, ui32CPUVAddr);
+    if (pmd_none(*psPMD) || pmd_bad(*psPMD))
+    {
+        PVR_ASSERT(0);
+    }
+       psPTE = (pte_t *)pte_offset_kernel(psPMD, ui32CPUVAddr);
+
+       ptent = ptep_modify_prot_start(&init_mm, ui32CPUVAddr, psPTE);
+       ptent = pte_mkwrite(ptent);
+       ptep_modify_prot_commit(&init_mm, ui32CPUVAddr, psPTE, ptent);
+
+       flush_tlb_all();
+}
+
+static IMG_VOID MakeKernelPageReadOnly(IMG_PVOID ulCPUVAddr)
+{
+    pgd_t *psPGD;
+    pud_t *psPUD;
+    pmd_t *psPMD;
+    pte_t *psPTE;
+    pte_t ptent;
+    IMG_UINT32 ui32CPUVAddr = (IMG_UINT32) ulCPUVAddr;
+
+       OSWriteMemoryBarrier();
+
+    psPGD = pgd_offset_k(ui32CPUVAddr);
+    if (pgd_none(*psPGD) || pgd_bad(*psPGD))
+    {
+        PVR_ASSERT(0);
+    }
+
+    psPUD = pud_offset(psPGD, ui32CPUVAddr);
+    if (pud_none(*psPUD) || pud_bad(*psPUD))
+    {
+        PVR_ASSERT(0);
+    }
+
+    psPMD = pmd_offset(psPUD, ui32CPUVAddr);
+    if (pmd_none(*psPMD) || pmd_bad(*psPMD))
+    {
+        PVR_ASSERT(0);
+    }
+
+       psPTE = (pte_t *)pte_offset_kernel(psPMD, ui32CPUVAddr);
+
+       ptent = ptep_modify_prot_start(&init_mm, ui32CPUVAddr, psPTE);
+       ptent = pte_wrprotect(ptent);
+       ptep_modify_prot_commit(&init_mm, ui32CPUVAddr, psPTE, ptent);
+
+       flush_tlb_all();
+
+}
+
+#else /* defined(PVRSRV_MMU_MAKE_READWRITE_ON_DEMAND) */
+
+static INLINE IMG_VOID MakeKernelPageReadWrite(IMG_PVOID ulCPUVAddr)
+{
+       PVR_UNREFERENCED_PARAMETER(ulCPUVAddr);
+}
+
+static INLINE IMG_VOID MakeKernelPageReadOnly(IMG_PVOID ulCPUVAddr)
+{
+       PVR_UNREFERENCED_PARAMETER(ulCPUVAddr);
 }
-#endif 
 
+#endif /* defined(PVRSRV_MMU_MAKE_READWRITE_ON_DEMAND) */
+
+/*___________________________________________________________________________
+
+       Information for SUPPORT_PDUMP_MULTI_PROCESS feature.
+       
+       The client marked for pdumping will set the bPDumpActive flag in
+       the MMU Context (see MMU_Initialise).
+       
+       Shared heap allocations should be persistent so all apps which
+       are pdumped will see the allocation. Persistent flag over-rides
+       the bPDumpActive flag (see pdump_common.c/DbgWrite function).
+       
+       The idea is to dump PT,DP for shared heap allocations, but only
+       dump the PDE if the allocation is mapped into the kernel or active
+       client context. This ensures if a background app allocates on a
+       shared heap then all clients can access it in the pdump toolchain.
+       
+       
+       
+       PD              PT              DP
+       +-+
+       | |---> +-+
+       +-+             | |---> +-+
+                       +-+             + +
+                                       +-+
+                                       
+       PD allocation/free: pdump flags are 0 (only need PD for active apps)
+       PT allocation/free: pdump flags are 0
+                                               unless PT is for a shared heap, in which case persistent is set
+       PD entries (MMU init/insert shared heap):
+                                               only pdump if PDE is on the active MMU context, flags are 0
+       PD entries (PT alloc):
+                                               pdump flags are 0 if kernel heap
+                                               pdump flags are 0 if shared heap and PDE is on active MMU context
+                                               otherwise ignore.
+       PT entries                      pdump flags are 0
+                                               unless PTE is for a shared heap, in which case persistent is set
+                                               
+       NOTE: PDump common code:-
+       PDumpMallocPages and PDumpMemKM also set the persistent flag for
+       shared heap allocations.
+       
+  ___________________________________________________________________________
+*/
+
+
+/*!
+******************************************************************************
+       FUNCTION:   MMU_IsHeapShared
 
+       PURPOSE:    Is this heap shared?
+       PARAMETERS: In: pMMU_Heap
+       RETURNS:    true if heap is shared
+******************************************************************************/
 IMG_BOOL MMU_IsHeapShared(MMU_HEAP* pMMUHeap)
 {
        switch(pMMUHeap->psDevArena->DevMemHeapType)
@@ -264,78 +526,145 @@ IMG_BOOL MMU_IsHeapShared(MMU_HEAP* pMMUHeap)
 }
 
 #ifdef SUPPORT_SGX_MMU_BYPASS
+/*!
+******************************************************************************
+       FUNCTION:   EnableHostAccess
+
+       PURPOSE:    Enables Host accesses to device memory, by passing the device
+                               MMU address translation
+
+       PARAMETERS: In: psMMUContext
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID
 EnableHostAccess (MMU_CONTEXT *psMMUContext)
 {
        IMG_UINT32 ui32RegVal;
        IMG_VOID *pvRegsBaseKM = psMMUContext->psDevInfo->pvRegsBaseKM;
 
-       
-
-
+       /*
+               bypass the MMU for the host port requestor,
+               conserving bypass state of other requestors
+       */
        ui32RegVal = OSReadHWReg(pvRegsBaseKM, EUR_CR_BIF_CTRL);
 
        OSWriteHWReg(pvRegsBaseKM,
                                EUR_CR_BIF_CTRL,
                                ui32RegVal | EUR_CR_BIF_CTRL_MMU_BYPASS_HOST_MASK);
-       
+       /* assume we're not wiping-out any other bits */
        PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_BIF_CTRL, EUR_CR_BIF_CTRL_MMU_BYPASS_HOST_MASK);
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   DisableHostAccess
+
+       PURPOSE:    Disables Host accesses to device memory, by passing the device
+                               MMU address translation
+
+       PARAMETERS: In: psMMUContext
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID
 DisableHostAccess (MMU_CONTEXT *psMMUContext)
 {
        IMG_UINT32 ui32RegVal;
        IMG_VOID *pvRegsBaseKM = psMMUContext->psDevInfo->pvRegsBaseKM;
 
-       
-
-
-
+       /*
+               disable MMU-bypass for the host port requestor,
+               conserving bypass state of other requestors
+               and flushing all caches/tlbs
+       */
        OSWriteHWReg(pvRegsBaseKM,
                                EUR_CR_BIF_CTRL,
                                ui32RegVal & ~EUR_CR_BIF_CTRL_MMU_BYPASS_HOST_MASK);
-       
+       /* assume we're not wiping-out any other bits */
        PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_BIF_CTRL, 0);
 }
 #endif
 
 
 #if defined(SGX_FEATURE_SYSTEM_CACHE)
+/*!
+******************************************************************************
+       FUNCTION:   MMU_InvalidateSystemLevelCache
+
+       PURPOSE:    Invalidates the System Level Cache to purge stale PDEs and PTEs
+
+       PARAMETERS: In: psDevInfo
+       RETURNS:    None
+
+******************************************************************************/
 static IMG_VOID MMU_InvalidateSystemLevelCache(PVRSRV_SGXDEV_INFO *psDevInfo)
 {
        #if defined(SGX_FEATURE_MP)
        psDevInfo->ui32CacheControl |= SGXMKIF_CC_INVAL_BIF_SL;
        #else
-       
+       /* The MMU always bypasses the SLC */
        PVR_UNREFERENCED_PARAMETER(psDevInfo);
-       #endif 
+       #endif /* SGX_FEATURE_MP */
 }
-#endif 
+#endif /* SGX_FEATURE_SYSTEM_CACHE */
+
+/*!
+******************************************************************************
+       FUNCTION:   MMU_InvalidateDirectoryCache
 
+       PURPOSE:    Invalidates the page directory cache + page table cache + requestor TLBs
+
+       PARAMETERS: In: psDevInfo
+       RETURNS:    None
+
+******************************************************************************/
 IMG_VOID MMU_InvalidateDirectoryCache(PVRSRV_SGXDEV_INFO *psDevInfo)
 {
        psDevInfo->ui32CacheControl |= SGXMKIF_CC_INVAL_BIF_PD;
        #if defined(SGX_FEATURE_SYSTEM_CACHE)
        MMU_InvalidateSystemLevelCache(psDevInfo);
-       #endif 
+       #endif /* SGX_FEATURE_SYSTEM_CACHE */
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_InvalidatePageTableCache
+
+       PURPOSE:    Invalidates the page table cache + requestor TLBs
+
+       PARAMETERS: In: psDevInfo
+       RETURNS:    None
+
+******************************************************************************/
 static IMG_VOID MMU_InvalidatePageTableCache(PVRSRV_SGXDEV_INFO *psDevInfo)
 {
        psDevInfo->ui32CacheControl |= SGXMKIF_CC_INVAL_BIF_PT;
        #if defined(SGX_FEATURE_SYSTEM_CACHE)
        MMU_InvalidateSystemLevelCache(psDevInfo);
-       #endif 
+       #endif /* SGX_FEATURE_SYSTEM_CACHE */
 }
 
 #if defined(FIX_HW_BRN_31620)
+/*!
+******************************************************************************
+       FUNCTION:   BRN31620InvalidatePageTableEntry
+
+       PURPOSE:    Frees page tables in PDE cache line chunks re-wiring the
+                   dummy page when required
+
+       PARAMETERS: In: psMMUContext, ui32PDIndex, ui32PTIndex
+       RETURNS:    None
+
+******************************************************************************/
 static IMG_VOID BRN31620InvalidatePageTableEntry(MMU_CONTEXT *psMMUContext, IMG_UINT32 ui32PDIndex, IMG_UINT32 ui32PTIndex, IMG_UINT32 *pui32PTE)
 {
        PVRSRV_SGXDEV_INFO *psDevInfo = psMMUContext->psDevInfo;
 
-       
+       /*
+        * Note: We can't tell at this stage if this PT will be freed before
+        * the end of the function so we always wire up the dummy page to
+        * to the PT.
+        */
        if (((ui32PDIndex % (BRN31620_PDE_CACHE_FILL_SIZE/BRN31620_PT_ADDRESS_RANGE_SIZE)) == BRN31620_DUMMY_PDE_INDEX)
                && (ui32PTIndex == BRN31620_DUMMY_PTE_INDEX))
        {
@@ -350,6 +679,17 @@ static IMG_VOID BRN31620InvalidatePageTableEntry(MMU_CONTEXT *psMMUContext, IMG_
        }
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   BRN31620FreePageTable
+
+       PURPOSE:    Frees page tables in PDE cache line chunks re-wiring the
+                   dummy page when required
+
+       PARAMETERS: In: psMMUContext, ui32PDIndex
+       RETURNS:    IMG_TRUE if we freed any PT's
+
+******************************************************************************/
 static IMG_BOOL BRN31620FreePageTable(MMU_HEAP *psMMUHeap, IMG_UINT32 ui32PDIndex)
 {
        MMU_CONTEXT *psMMUContext = psMMUHeap->psMMUContext;
@@ -360,13 +700,18 @@ static IMG_BOOL BRN31620FreePageTable(MMU_HEAP *psMMUHeap, IMG_UINT32 ui32PDInde
 
        PVR_ASSERT(psMMUHeap != IMG_NULL);
 
-       
+       /* 
+        * Clear the PT info for this PD index so even if we don't
+        * free the memory here apsPTInfoList[PDIndex] will trigger
+        * an "allocation" in _DeferredAllocPagetables which
+        * bumps up the refcount.
+        */
        PVR_ASSERT(psMMUContext->apsPTInfoListSave[ui32PDIndex] == IMG_NULL);
 
        psMMUContext->apsPTInfoListSave[ui32PDIndex] = psMMUContext->apsPTInfoList[ui32PDIndex];
        psMMUContext->apsPTInfoList[ui32PDIndex] = IMG_NULL;
 
-       
+       /* Check if this was the last PT in the cache line */
        if (--psMMUContext->ui32PDCacheRangeRefCount[ui32PDCacheLine] == 0)
        {
                IMG_UINT32 i;
@@ -374,10 +719,10 @@ static IMG_BOOL BRN31620FreePageTable(MMU_HEAP *psMMUHeap, IMG_UINT32 ui32PDInde
                IMG_UINT32 ui32PDIndexEnd = ui32PDIndexStart + BRN31620_PDES_PER_CACHE_LINE_SIZE;
                IMG_UINT32 ui32PDBitMaskIndex, ui32PDBitMaskShift;
 
-               
+               /* Free all PT's in cache line */
                for (i=ui32PDIndexStart;i<ui32PDIndexEnd;i++)
                {
-                       
+                       /* This PT is _really_ being freed now */
                        psMMUContext->apsPTInfoList[i] = psMMUContext->apsPTInfoListSave[i];
                        psMMUContext->apsPTInfoListSave[i] = IMG_NULL;
                        _DeferredFreePageTable(psMMUHeap, i - psMMUHeap->ui32PDBaseIndex, IMG_TRUE);
@@ -386,22 +731,27 @@ static IMG_BOOL BRN31620FreePageTable(MMU_HEAP *psMMUHeap, IMG_UINT32 ui32PDInde
                ui32PDBitMaskIndex = ui32PDCacheLine >> BRN31620_CACHE_FLUSH_BITS_SHIFT;
                ui32PDBitMaskShift = ui32PDCacheLine & BRN31620_CACHE_FLUSH_BITS_MASK;
 
-               
+               /* Check if this is a shared heap */
                if (MMU_IsHeapShared(psMMUHeap))
                {
-                       
+                       /* Mark the remove of the Page Table from all memory contexts */
                        MMU_CONTEXT *psMMUContextWalker = (MMU_CONTEXT*) psMMUHeap->psMMUContext->psDevInfo->pvMMUContextList;
 
                        while(psMMUContextWalker)
                        {
                                psMMUContextWalker->ui32PDChangeMask[ui32PDBitMaskIndex] |= 1 << ui32PDBitMaskShift;
 
-                               
+                               /*
+                                * We've just cleared a cache line's worth of PDE's so we need
+                                * to wire up the dummy PT
+                                */
+                               MakeKernelPageReadWrite(psMMUContextWalker->pvPDCpuVAddr);
                                pui32Tmp = (IMG_UINT32 *) psMMUContextWalker->pvPDCpuVAddr;
                                pui32Tmp[ui32PDIndexStart + BRN31620_DUMMY_PDE_INDEX] = (psDevInfo->sBRN31620DummyPTDevPAddr.uiAddr>>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                                                                                | SGX_MMU_PDE_PAGE_SIZE_4K
                                                                                                | SGX_MMU_PDE_DUMMY_PAGE
                                                                                                | SGX_MMU_PDE_VALID;
+                               MakeKernelPageReadOnly(psMMUContextWalker->pvPDCpuVAddr);
 
                                PDUMPCOMMENT("BRN31620 Re-wire dummy PT due to releasing PT allocation block");
                                PDUMPPDENTRIES(&psMMUHeap->sMMUAttrib, psMMUContextWalker->hPDOSMemHandle, (IMG_VOID*)&pui32Tmp[ui32PDIndexStart + BRN31620_DUMMY_PDE_INDEX], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PT_UNIQUETAG, PDUMP_PT_UNIQUETAG);
@@ -412,17 +762,22 @@ static IMG_BOOL BRN31620FreePageTable(MMU_HEAP *psMMUHeap, IMG_UINT32 ui32PDInde
                {
                        psMMUContext->ui32PDChangeMask[ui32PDBitMaskIndex] |= 1 << ui32PDBitMaskShift;
 
-                       
+                       /*
+                        * We've just cleared a cache line's worth of PDE's so we need
+                        * to wire up the dummy PT
+                        */
+                       MakeKernelPageReadWrite(psMMUContext->pvPDCpuVAddr);
                        pui32Tmp = (IMG_UINT32 *) psMMUContext->pvPDCpuVAddr;
                        pui32Tmp[ui32PDIndexStart + BRN31620_DUMMY_PDE_INDEX] = (psDevInfo->sBRN31620DummyPTDevPAddr.uiAddr>>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                                                                        | SGX_MMU_PDE_PAGE_SIZE_4K
                                                                                        | SGX_MMU_PDE_DUMMY_PAGE
                                                                                        | SGX_MMU_PDE_VALID;
+                       MakeKernelPageReadOnly(psMMUContext->pvPDCpuVAddr);
 
                        PDUMPCOMMENT("BRN31620 Re-wire dummy PT due to releasing PT allocation block");
                        PDUMPPDENTRIES(&psMMUHeap->sMMUAttrib, psMMUContext->hPDOSMemHandle, (IMG_VOID*)&pui32Tmp[ui32PDIndexStart + BRN31620_DUMMY_PDE_INDEX], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PT_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                }
-               
+               /* We've freed a cachline's worth of PDE's so trigger a PD cache flush */
                bFreePTs = IMG_TRUE;
        }
 
@@ -430,6 +785,18 @@ static IMG_BOOL BRN31620FreePageTable(MMU_HEAP *psMMUHeap, IMG_UINT32 ui32PDInde
 }
 #endif
 
+/*!
+******************************************************************************
+       FUNCTION:   _AllocPageTableMemory
+
+       PURPOSE:    Allocate physical memory for a page table
+
+       PARAMETERS: In: pMMUHeap - the mmu
+                               In: psPTInfoList - PT info
+                               Out: psDevPAddr - device physical address for new PT
+       RETURNS:    IMG_TRUE - Success
+                   IMG_FALSE - Failed
+******************************************************************************/
 static IMG_BOOL
 _AllocPageTableMemory (MMU_HEAP *pMMUHeap,
                                                MMU_PT_INFO *psPTInfoList,
@@ -438,23 +805,33 @@ _AllocPageTableMemory (MMU_HEAP *pMMUHeap,
        IMG_DEV_PHYADDR sDevPAddr;
        IMG_CPU_PHYADDR sCpuPAddr;
 
-       
-
-
+       /*
+               depending on the specific system, pagetables are allocated from system memory
+               or device local memory.  For now, just look for at least a valid local heap/arena
+       */
        if(pMMUHeap->psDevArena->psDeviceMemoryHeapInfo->psLocalDevMemArena == IMG_NULL)
        {
-               
+               //FIXME: replace with an RA, this allocator only handles 4k allocs
                if (OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                  pMMUHeap->ui32PTSize,
-                                                  SGX_MMU_PAGE_SIZE,
-                                                  (IMG_VOID **)&psPTInfoList->PTPageCpuVAddr,
-                                                  &psPTInfoList->hPTPageOSMemHandle) != PVRSRV_OK)
+                                                pMMUHeap->ui32PTSize,
+                                                SGX_MMU_PAGE_SIZE,//FIXME: assume 4K page size for now (wastes memory for smaller pagetables
+                                                IMG_NULL,
+                                                0,
+                                                IMG_NULL,
+                                                (IMG_VOID **)&psPTInfoList->PTPageCpuVAddr,
+                                                &psPTInfoList->hPTPageOSMemHandle) != PVRSRV_OK)
                {
                        PVR_DPF((PVR_DBG_ERROR, "_AllocPageTableMemory: ERROR call to OSAllocPages failed"));
                        return IMG_FALSE;
                }
 
-               
+               /*
+                       Force the page to read only, we will make it read/write as
+                       and when we need to
+               */
+               MakeKernelPageReadOnly(psPTInfoList->PTPageCpuVAddr);
+
+               /* translate address to device physical */
                if(psPTInfoList->PTPageCpuVAddr)
                {
                        sCpuPAddr = OSMapLinToCPUPhys(psPTInfoList->hPTPageOSMemHandle,
@@ -462,7 +839,8 @@ _AllocPageTableMemory (MMU_HEAP *pMMUHeap,
                }
                else
                {
-                       
+                       /* This isn't used in all cases since not all ports currently support
+                        * OSMemHandleToCpuPAddr() */
                        sCpuPAddr = OSMemHandleToCpuPAddr(psPTInfoList->hPTPageOSMemHandle, 0);
                }
 
@@ -472,16 +850,19 @@ _AllocPageTableMemory (MMU_HEAP *pMMUHeap,
        {
                IMG_SYS_PHYADDR sSysPAddr;
 
-               
-
-
-               
+               /*
+                       just allocate from the first local memory arena
+                       (unlikely to be more than one local mem area(?))
+               */
+               //FIXME: just allocate a 4K page for each PT for now
                if(RA_Alloc(pMMUHeap->psDevArena->psDeviceMemoryHeapInfo->psLocalDevMemArena,
-                                       SGX_MMU_PAGE_SIZE,
+                                       SGX_MMU_PAGE_SIZE,//pMMUHeap->ui32PTSize,
                                        IMG_NULL,
                                        IMG_NULL,
                                        0,
-                                       SGX_MMU_PAGE_SIZE,
+                                       SGX_MMU_PAGE_SIZE,//pMMUHeap->ui32PTSize,
+                                       0,
+                                       IMG_NULL,
                                        0,
                                        &(sSysPAddr.uiAddr))!= IMG_TRUE)
                {
@@ -489,9 +870,9 @@ _AllocPageTableMemory (MMU_HEAP *pMMUHeap,
                        return IMG_FALSE;
                }
 
-               
+               /* derive the CPU virtual address */
                sCpuPAddr = SysSysPAddrToCpuPAddr(sSysPAddr);
-               
+               /* note: actual ammount is pMMUHeap->ui32PTSize but must be a multiple of 4k pages */
                psPTInfoList->PTPageCpuVAddr = OSMapPhysToLin(sCpuPAddr,
                                                                                                        SGX_MMU_PAGE_SIZE,
                                                                                                        PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
@@ -502,7 +883,7 @@ _AllocPageTableMemory (MMU_HEAP *pMMUHeap,
                        return IMG_FALSE;
                }
 
-               
+               /* translate address to device physical */
                sDevPAddr = SysCpuPAddrToDevPAddr (PVRSRV_DEVICE_TYPE_SGX, sCpuPAddr);
 
                #if PAGE_TEST
@@ -510,60 +891,76 @@ _AllocPageTableMemory (MMU_HEAP *pMMUHeap,
                #endif
        }
 
+       MakeKernelPageReadWrite(psPTInfoList->PTPageCpuVAddr);
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
        {
                IMG_UINT32 *pui32Tmp;
                IMG_UINT32 i;
 
                pui32Tmp = (IMG_UINT32*)psPTInfoList->PTPageCpuVAddr;
-               
+               /* point the new PT entries to the dummy data page */
                for(i=0; i<pMMUHeap->ui32PTNumEntriesUsable; i++)
                {
                        pui32Tmp[i] = (pMMUHeap->psMMUContext->psDevInfo->sDummyDataDevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                | SGX_MMU_PTE_VALID;
                }
-               
+               /* zero the remaining allocated entries, if any */
                for(; i<pMMUHeap->ui32PTNumEntriesAllocated; i++)
                {
                        pui32Tmp[i] = 0;
                }
        }
 #else
-       
+       /* Zero the page table. */
        OSMemSet(psPTInfoList->PTPageCpuVAddr, 0, pMMUHeap->ui32PTSize);
 #endif
+       MakeKernelPageReadOnly(psPTInfoList->PTPageCpuVAddr);
 
 #if defined(PDUMP)
        {
                IMG_UINT32 ui32Flags = 0;
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-               
+               /* make sure shared heap PT allocs are always pdumped */
                ui32Flags |= ( MMU_IsHeapShared(pMMUHeap) ) ? PDUMP_FLAGS_PERSISTENT : 0;
 #endif
-               
+               /* pdump the PT malloc */
                PDUMPMALLOCPAGETABLE(&pMMUHeap->psMMUContext->psDeviceNode->sDevId, psPTInfoList->hPTPageOSMemHandle, 0, psPTInfoList->PTPageCpuVAddr, pMMUHeap->ui32PTSize, ui32Flags, PDUMP_PT_UNIQUETAG);
-               
+               /* pdump the PT Pages */
                PDUMPMEMPTENTRIES(&pMMUHeap->sMMUAttrib, psPTInfoList->hPTPageOSMemHandle, psPTInfoList->PTPageCpuVAddr, pMMUHeap->ui32PTSize, ui32Flags, IMG_TRUE, PDUMP_PT_UNIQUETAG, PDUMP_PT_UNIQUETAG);
        }
 #endif
-       
-       
+
+       /* return the DevPAddr */
        *psDevPAddr = sDevPAddr;
 
        return IMG_TRUE;
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   _FreePageTableMemory
+
+       PURPOSE:    Free physical memory for a page table
+
+       PARAMETERS: In: pMMUHeap - the mmu
+                               In: psPTInfoList - PT info to free
+       RETURNS:    NONE
+******************************************************************************/
 static IMG_VOID
 _FreePageTableMemory (MMU_HEAP *pMMUHeap, MMU_PT_INFO *psPTInfoList)
 {
-       
-
-
-
+       /*
+               free the PT page:
+               depending on the specific system, pagetables are allocated from system memory
+               or device local memory.  For now, just look for at least a valid local heap/arena
+       */
        if(pMMUHeap->psDevArena->psDeviceMemoryHeapInfo->psLocalDevMemArena == IMG_NULL)
        {
-               
+               /* Force the page to read write before we free it*/
+               MakeKernelPageReadWrite(psPTInfoList->PTPageCpuVAddr);
+
+               //FIXME: replace with an RA, this allocator only handles 4k allocs
                OSFreePages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
                                          pMMUHeap->ui32PTSize,
                                          psPTInfoList->PTPageCpuVAddr,
@@ -574,27 +971,39 @@ _FreePageTableMemory (MMU_HEAP *pMMUHeap, MMU_PT_INFO *psPTInfoList)
                IMG_SYS_PHYADDR sSysPAddr;
                IMG_CPU_PHYADDR sCpuPAddr;
 
-               
+               /*  derive the system physical address */
                sCpuPAddr = OSMapLinToCPUPhys(psPTInfoList->hPTPageOSMemHandle, 
                                                                          psPTInfoList->PTPageCpuVAddr);
                sSysPAddr = SysCpuPAddrToSysPAddr (sCpuPAddr);
 
-               
-               
+               /* unmap the CPU mapping */
+               /* note: actual ammount is pMMUHeap->ui32PTSize but must be a multiple of 4k pages */
                OSUnMapPhysToLin(psPTInfoList->PTPageCpuVAddr,
                          SGX_MMU_PAGE_SIZE,
                          PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
                          psPTInfoList->hPTPageOSMemHandle);
 
-               
-
-
+               /*
+                       just free from the first local memory arena
+                       (unlikely to be more than one local mem area(?))
+               */
                RA_Free (pMMUHeap->psDevArena->psDeviceMemoryHeapInfo->psLocalDevMemArena, sSysPAddr.uiAddr, IMG_FALSE);
        }
 }
 
 
 
+/*!
+******************************************************************************
+       FUNCTION:   _DeferredFreePageTable
+
+       PURPOSE:    Free one page table associated with an MMU.
+
+       PARAMETERS: In:  pMMUHeap - the mmu heap
+                               In:  ui32PTIndex - index of the page table to free relative
+                                                                  to the base of heap.
+       RETURNS:    None
+******************************************************************************/
 static IMG_VOID
 _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOSFreePT)
 {
@@ -606,10 +1015,10 @@ _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOS
 
        SysAcquireData(&psSysData);
 
-       
+       /* find the index/offset in PD entries  */
        ui32PDIndex = pMMUHeap->psDevArena->BaseDevVAddr.uiAddr >> pMMUHeap->ui32PDShift;
 
-       
+       /* set the base PT info */
        ppsPTInfoList = &pMMUHeap->psMMUContext->apsPTInfoList[ui32PDIndex];
 
        {
@@ -617,11 +1026,11 @@ _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOS
                if(ppsPTInfoList[ui32PTIndex] && ppsPTInfoList[ui32PTIndex]->ui32ValidPTECount > 0)
                {
                        DumpPT(ppsPTInfoList[ui32PTIndex]);
-                       
+                       /* Fall-through, will fail assert */
                }
 #endif
 
-               
+               /* Assert that all mappings have gone */
                PVR_ASSERT(ppsPTInfoList[ui32PTIndex] == IMG_NULL || ppsPTInfoList[ui32PTIndex]->ui32ValidPTECount == 0);
        }
 
@@ -631,7 +1040,7 @@ _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOS
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
                ui32Flags |= ( MMU_IsHeapShared(pMMUHeap) ) ? PDUMP_FLAGS_PERSISTENT : 0;
 #endif
-               
+               /* pdump the PT free */
                PDUMPCOMMENT("Free page table (page count == %08X)", pMMUHeap->ui32PageTableCount);
                if(ppsPTInfoList[ui32PTIndex] && ppsPTInfoList[ui32PTIndex]->PTPageCpuVAddr)
                {
@@ -645,30 +1054,32 @@ _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOS
                case DEVICE_MEMORY_HEAP_SHARED :
                case DEVICE_MEMORY_HEAP_SHARED_EXPORTED :
                {
-                       
+                       /* Remove Page Table from all memory contexts */
                        MMU_CONTEXT *psMMUContext = (MMU_CONTEXT*)pMMUHeap->psMMUContext->psDevInfo->pvMMUContextList;
 
                        while(psMMUContext)
                        {
-                               
+                               /* get the PD CPUVAddr base and advance to the first entry */
+                               MakeKernelPageReadWrite(psMMUContext->pvPDCpuVAddr);
                                pui32PDEntry = (IMG_UINT32*)psMMUContext->pvPDCpuVAddr;
                                pui32PDEntry += ui32PDIndex;
 
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-                               
+                               /* point the PD entry to the dummy PT */
                                pui32PDEntry[ui32PTIndex] = (psMMUContext->psDevInfo->sDummyPTDevPAddr.uiAddr
                                                                                        >>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                                                                        | SGX_MMU_PDE_PAGE_SIZE_4K
                                                                                        | SGX_MMU_PDE_VALID;
 #else
-                               
+                               /* free the entry */
                                if(bOSFreePT)
                                {
                                        pui32PDEntry[ui32PTIndex] = 0;
                                }
 #endif
+                               MakeKernelPageReadOnly(psMMUContext->pvPDCpuVAddr);
                        #if defined(PDUMP)
-                               
+                               /* pdump the PD Page modifications */
                        #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
                                if(psMMUContext->bPDumpActive)
                        #endif
@@ -676,7 +1087,7 @@ _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOS
                                        PDUMPPDENTRIES(&pMMUHeap->sMMUAttrib, psMMUContext->hPDOSMemHandle, (IMG_VOID*)&pui32PDEntry[ui32PTIndex], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PT_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                                }
                        #endif
-                               
+                               /* advance to next context */
                                psMMUContext = psMMUContext->psNext;
                        }
                        break;
@@ -684,25 +1095,27 @@ _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOS
                case DEVICE_MEMORY_HEAP_PERCONTEXT :
                case DEVICE_MEMORY_HEAP_KERNEL :
                {
-                       
+                       MakeKernelPageReadWrite(pMMUHeap->psMMUContext->pvPDCpuVAddr);
+                       /* Remove Page Table from this memory context only */
                        pui32PDEntry = (IMG_UINT32*)pMMUHeap->psMMUContext->pvPDCpuVAddr;
                        pui32PDEntry += ui32PDIndex;
 
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-                       
+                       /* point the PD entry to the dummy PT */
                        pui32PDEntry[ui32PTIndex] = (pMMUHeap->psMMUContext->psDevInfo->sDummyPTDevPAddr.uiAddr
                                                                                >>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                                                                | SGX_MMU_PDE_PAGE_SIZE_4K
                                                                                | SGX_MMU_PDE_VALID;
 #else
-                       
+                       /* free the entry */
                        if(bOSFreePT)
                        {
                                pui32PDEntry[ui32PTIndex] = 0;
                        }
 #endif
+                       MakeKernelPageReadOnly(pMMUHeap->psMMUContext->pvPDCpuVAddr);
 
-                       
+                       /* pdump the PD Page modifications */
                        PDUMPPDENTRIES(&pMMUHeap->sMMUAttrib, pMMUHeap->psMMUContext->hPDOSMemHandle, (IMG_VOID*)&pui32PDEntry[ui32PTIndex], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                        break;
                }
@@ -713,45 +1126,49 @@ _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOS
                }
        }
 
-       
+       /* clear the PT entries in each PT page */
        if(ppsPTInfoList[ui32PTIndex] != IMG_NULL)
        {
                if(ppsPTInfoList[ui32PTIndex]->PTPageCpuVAddr != IMG_NULL)
                {
                        IMG_PUINT32 pui32Tmp;
 
+                       MakeKernelPageReadWrite(ppsPTInfoList[ui32PTIndex]->PTPageCpuVAddr);
                        pui32Tmp = (IMG_UINT32*)ppsPTInfoList[ui32PTIndex]->PTPageCpuVAddr;
 
-                       
+                       /* clear the entries */
                        for(i=0;
                                (i<pMMUHeap->ui32PTETotalUsable) && (i<pMMUHeap->ui32PTNumEntriesUsable);
                                 i++)
                        {
-                               
+                               /* over-allocated PT entries for 4MB data page case should never be non-zero */
                                pui32Tmp[i] = 0;
                        }
+                       MakeKernelPageReadOnly(ppsPTInfoList[ui32PTIndex]->PTPageCpuVAddr);
 
-                       
-
+                       /*
+                               free the pagetable memory
+                       */
                        if(bOSFreePT)
                        {
                                _FreePageTableMemory(pMMUHeap, ppsPTInfoList[ui32PTIndex]);
                        }
 
-                       
-
-
+                       /*
+                               decrement the PT Entry Count by the number
+                               of entries we've cleared in this pass
+                       */
                        pMMUHeap->ui32PTETotalUsable -= i;
                }
                else
                {
-                       
+                       /* decrement the PT Entry Count by a page's worth of entries  */
                        pMMUHeap->ui32PTETotalUsable -= pMMUHeap->ui32PTNumEntriesUsable;
                }
 
                if(bOSFreePT)
                {
-                       
+                       /* free the pt info */
                        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
                                                sizeof(MMU_PT_INFO),
                                                ppsPTInfoList[ui32PTIndex],
@@ -761,13 +1178,22 @@ _DeferredFreePageTable (MMU_HEAP *pMMUHeap, IMG_UINT32 ui32PTIndex, IMG_BOOL bOS
        }
        else
        {
-               
+               /* decrement the PT Entry Count by a page's worth of usable entries */
                pMMUHeap->ui32PTETotalUsable -= pMMUHeap->ui32PTNumEntriesUsable;
        }
 
        PDUMPCOMMENT("Finished free page table (page count == %08X)", pMMUHeap->ui32PageTableCount);
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   _DeferredFreePageTables
+
+       PURPOSE:    Free the page tables associated with an MMU.
+
+       PARAMETERS: In:  pMMUHeap - the mmu
+       RETURNS:    None
+******************************************************************************/
 static IMG_VOID
 _DeferredFreePageTables (MMU_HEAP *pMMUHeap)
 {
@@ -794,14 +1220,17 @@ _DeferredFreePageTables (MMU_HEAP *pMMUHeap)
                {
                        if (psMMUContext->apsPTInfoList[ui32PDIndex]->PTPageCpuVAddr)
                        {
-                               
+                               /*
+                                * We have to do this to setup the dummy page as
+                                * not all heaps are PD cache size or aligned
+                                */
                                for (j=0;j<SGX_MMU_PT_SIZE;j++)
                                {
                                        pui32Tmp = (IMG_UINT32 *) psMMUContext->apsPTInfoList[ui32PDIndex]->PTPageCpuVAddr;
                                        BRN31620InvalidatePageTableEntry(psMMUContext, ui32PDIndex, j, &pui32Tmp[j]);
                                }
                        }
-                       
+                       /* Free the PT and NULL's out the PTInfo */
                        if (BRN31620FreePageTable(pMMUHeap, ui32PDIndex) == IMG_TRUE)
                        {
                                bInvalidateDirectoryCache = IMG_TRUE;
@@ -809,7 +1238,10 @@ _DeferredFreePageTables (MMU_HEAP *pMMUHeap)
                }
        }
 
-       
+       /*
+        * Due to freeing PT's in chunks we might need to flush the PT cache
+        * rather then the directory cache
+        */
        if (bInvalidateDirectoryCache)
        {
                MMU_InvalidateDirectoryCache(pMMUHeap->psMMUContext->psDevInfo);
@@ -828,6 +1260,18 @@ _DeferredFreePageTables (MMU_HEAP *pMMUHeap)
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   _DeferredAllocPagetables
+
+       PURPOSE:    allocates page tables at time of allocation
+
+       PARAMETERS: In:  pMMUHeap - the mmu heap
+                                        DevVAddr - devVAddr of allocation
+                                        ui32Size - size of allocation
+       RETURNS:    IMG_TRUE - Success
+                   IMG_FALSE - Failed
+******************************************************************************/
 static IMG_BOOL
 _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT32 ui32Size)
 {
@@ -848,23 +1292,23 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
        IMG_UINT32 ui32ModifiedCachelines[BRN31620_CACHE_FLUSH_INDEX_SIZE];
 #endif
 
-       
+       /* Check device linear address */
 #if SGX_FEATURE_ADDRESS_SPACE_SIZE < 32
        PVR_ASSERT(DevVAddr.uiAddr < (1<<SGX_FEATURE_ADDRESS_SPACE_SIZE));
 #endif
 
-       
+       /* get the sysdata */
        SysAcquireData(&psSysData);
 
-       
+       /* find the index/offset in PD entries  */
        ui32PDIndex = DevVAddr.uiAddr >> pMMUHeap->ui32PDShift;
 
-       
-       
+       /* how many PDs does the allocation occupy? */
+       /* first check for overflows */
        if((UINT32_MAX_VALUE - DevVAddr.uiAddr)
                < (ui32Size + pMMUHeap->ui32DataPageMask + pMMUHeap->ui32PTMask))
        {
-               
+               /* detected overflow, clamp to highest address */
                sHighDevVAddr.uiAddr = UINT32_MAX_VALUE;
        }
        else
@@ -877,7 +1321,7 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
 
        ui32PageTableCount = sHighDevVAddr.uiAddr >> pMMUHeap->ui32PDShift;
 
-       
+       /* Fix allocation of last 4MB */
        if (ui32PageTableCount == 0)
                ui32PageTableCount = 1024;
 
@@ -887,42 +1331,42 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                ui32ModifiedCachelines[i] = 0;
        }
 
-       
-       
-       
+       /*****************************************************************/
+       /* Save off requested data and round allocation to PD cache line */
+       /*****************************************************************/
        sDevVAddrRequestStart = DevVAddr;
        ui32PDRequestStart = ui32PDIndex;
        sDevVAddrRequestEnd = sHighDevVAddr;
        ui32PDRequestEnd = ui32PageTableCount - 1;
 
-       
+       /* Round allocations down to the PD cacheline */
        DevVAddr.uiAddr = DevVAddr.uiAddr & (~BRN31620_PDE_CACHE_FILL_MASK);
 
-       
+       /* Round the end address of the PD allocation to cacheline */
        sHighDevVAddr.uiAddr = ((sHighDevVAddr.uiAddr + (BRN31620_PDE_CACHE_FILL_SIZE - 1)) & (~BRN31620_PDE_CACHE_FILL_MASK));
 
        ui32PDIndex = DevVAddr.uiAddr >> pMMUHeap->ui32PDShift;
        ui32PageTableCount = sHighDevVAddr.uiAddr >> pMMUHeap->ui32PDShift;
 
-       
+       /* Fix allocation of last 4MB */
        if (ui32PageTableCount == 0)
                ui32PageTableCount = 1024;
 #endif
 
        ui32PageTableCount -= ui32PDIndex;
 
-       
+       /* get the PD CPUVAddr base and advance to the first entry */
        pui32PDEntry = (IMG_UINT32*)pMMUHeap->psMMUContext->pvPDCpuVAddr;
        pui32PDEntry += ui32PDIndex;
 
-       
+       /* and advance to the first PT info list */
        ppsPTInfoList = &pMMUHeap->psMMUContext->apsPTInfoList[ui32PDIndex];
 
 #if defined(PDUMP)
        {
                IMG_UINT32 ui32Flags = 0;
                
-               
+               /* pdump the PD Page modifications */
                if( MMU_IsHeapShared(pMMUHeap) )
                {
                        ui32Flags |= PDUMP_FLAGS_CONTINUOUS;
@@ -935,16 +1379,16 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                PDUMPCOMMENTWITHFLAGS(ui32Flags, "Page directory mods (page count == %08X)", ui32PageTableCount);
        }
 #endif
-       
+       /* walk the psPTInfoList to see what needs allocating: */
        for(i=0; i<ui32PageTableCount; i++)
        {
                if(ppsPTInfoList[i] == IMG_NULL)
                {
 #if defined(FIX_HW_BRN_31620)
-                       
+                       /* Check if we have a saved PT (i.e. this PDE cache line is still live) */
                        if (pMMUHeap->psMMUContext->apsPTInfoListSave[ui32PDIndex + i])
                        {
-                               
+                               /* Only make this PTInfo "live" if it's requested */
                                if (((ui32PDIndex + i) >= ui32PDRequestStart) && ((ui32PDIndex + i) <= ui32PDRequestEnd))
                                {
                                        IMG_UINT32 ui32PDCacheLine = (ui32PDIndex + i) >> BRN31620_PDES_PER_CACHE_LINE_SHIFT;
@@ -973,7 +1417,7 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
 #endif
                }
 #if defined(FIX_HW_BRN_31620)
-               
+               /* Only try to allocate if ppsPTInfoList[i] is valid */
                if (ppsPTInfoList[i])
                {
 #endif
@@ -986,7 +1430,7 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                        IMG_UINT32 j;
 #else
 #if !defined(FIX_HW_BRN_31620)
-                       
+                       /* no page table has been allocated so allocate one */
                        PVR_ASSERT(pui32PDEntry[i] == 0);
 #endif
 #endif
@@ -997,7 +1441,7 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                        }
 #if defined(FIX_HW_BRN_31620)
                        bFlushSystemCache = IMG_TRUE;
-                       
+                       /* Bump up the page table count if required */
                        {
                                IMG_UINT32 ui32PD;
                                IMG_UINT32 ui32PDCacheLine;
@@ -1010,7 +1454,7 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                                ui32PDBitMaskShift = ui32PDCacheLine & BRN31620_CACHE_FLUSH_BITS_MASK;
                                ui32ModifiedCachelines[ui32PDBitMaskIndex] |= 1 << ui32PDBitMaskShift;
 
-                               
+                               /* Add 1 to ui32PD as we want the count, not a range */
                                if ((pMMUHeap->ui32PDBaseIndex + pMMUHeap->ui32PageTableCount) < (ui32PD + 1))
                                {
                                        pMMUHeap->ui32PageTableCount = (ui32PD + 1) - pMMUHeap->ui32PDBaseIndex;
@@ -1027,30 +1471,32 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                                case DEVICE_MEMORY_HEAP_SHARED :
                                case DEVICE_MEMORY_HEAP_SHARED_EXPORTED :
                                {
-                                       
+                                       /* insert Page Table into all memory contexts */
                                        MMU_CONTEXT *psMMUContext = (MMU_CONTEXT*)pMMUHeap->psMMUContext->psDevInfo->pvMMUContextList;
 
                                        while(psMMUContext)
                                        {
-                                               
+                                               MakeKernelPageReadWrite(psMMUContext->pvPDCpuVAddr);
+                                               /* get the PD CPUVAddr base and advance to the first entry */
                                                pui32PDEntry = (IMG_UINT32*)psMMUContext->pvPDCpuVAddr;
                                                pui32PDEntry += ui32PDIndex;
 
-                                               
+                                               /* insert the page, specify the data page size and make the pde valid */
                                                pui32PDEntry[i] = (sDevPAddr.uiAddr>>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                                                                | pMMUHeap->ui32PDEPageSizeCtrl
                                                                                | SGX_MMU_PDE_VALID;
+                                               MakeKernelPageReadOnly(psMMUContext->pvPDCpuVAddr);
                                                #if defined(PDUMP)
-                                               
+                                               /* pdump the PD Page modifications */
                                                #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
                                                if(psMMUContext->bPDumpActive)
                                                #endif
                                                {
-                                                       
+                                                       //PDUMPCOMMENT("_DeferredAllocPTs: Dumping shared PDEs on context %d (%s)", psMMUContext->ui32PDumpMMUContextID, (psMMUContext->bPDumpActive) ? "active" : "");
                                                        PDUMPPDENTRIES(&pMMUHeap->sMMUAttrib, psMMUContext->hPDOSMemHandle, (IMG_VOID*)&pui32PDEntry[i], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                                                }
-                                               #endif 
-                                               
+                                               #endif /* PDUMP */
+                                               /* advance to next context */
                                                psMMUContext = psMMUContext->psNext;
                                        }
 #if defined(FIX_HW_BRN_31620)
@@ -1061,13 +1507,14 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                                case DEVICE_MEMORY_HEAP_PERCONTEXT :
                                case DEVICE_MEMORY_HEAP_KERNEL :
                                {
-                                       
+                                       MakeKernelPageReadWrite(pMMUHeap->psMMUContext->pvPDCpuVAddr);
+                                       /* insert Page Table into only this memory context */
                                        pui32PDEntry[i] = (sDevPAddr.uiAddr>>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                                                        | pMMUHeap->ui32PDEPageSizeCtrl
                                                                        | SGX_MMU_PDE_VALID;
-
-                                       
-                                       
+                                       MakeKernelPageReadOnly(pMMUHeap->psMMUContext->pvPDCpuVAddr);
+                                       /* pdump the PD Page modifications */
+                                       //PDUMPCOMMENT("_DeferredAllocPTs: Dumping kernel PDEs on context %d (%s)", pMMUHeap->psMMUContext->ui32PDumpMMUContextID, (pMMUHeap->psMMUContext->bPDumpActive) ? "active" : "");
                                        PDUMPPDENTRIES(&pMMUHeap->sMMUAttrib, pMMUHeap->psMMUContext->hPDOSMemHandle, (IMG_VOID*)&pui32PDEntry[i], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                                        break;
                                }
@@ -1079,14 +1526,15 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                        }
 
 #if !defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS)
-                       
-
-
-
+                       /* This is actually not to do with multiple mem contexts, but to do with the directory cache.
+                          In the 1 context implementation of the MMU, the directory "cache" is actually a copy of the
+                          page directory memory, and requires updating whenever the page directory changes, even if there
+                          was no previous value in a particular entry
+                        */
                        MMU_InvalidateDirectoryCache(pMMUHeap->psMMUContext->psDevInfo);
 #endif
 #if defined(FIX_HW_BRN_31620)
-                       
+                       /* If this PT is not in the requested range then save it and null out the main PTInfo */
                        if (((ui32PDIndex + i) < ui32PDRequestStart) || ((ui32PDIndex + i) > ui32PDRequestEnd))
                        {
                                        pMMUHeap->psMMUContext->apsPTInfoListSave[ui32PDIndex + i] = ppsPTInfoList[i];
@@ -1097,7 +1545,7 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                else
                {
 #if !defined(FIX_HW_BRN_31620)
-                       
+                       /* already have an allocated PT */
                        PVR_ASSERT(pui32PDEntry[i] != 0);
 #endif
                }
@@ -1108,20 +1556,20 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
 
        #if defined(SGX_FEATURE_SYSTEM_CACHE)
        #if defined(FIX_HW_BRN_31620)
-       
+       /* This function might not allocate any new PT's so check before flushing */
        if (bFlushSystemCache)
        {
        #endif
 
        MMU_InvalidateSystemLevelCache(pMMUHeap->psMMUContext->psDevInfo);
-       #endif 
+       #endif /* SGX_FEATURE_SYSTEM_CACHE */
        #if defined(FIX_HW_BRN_31620)
        }
 
-       
+       /* Handle the last 4MB roll over */
        sHighDevVAddr.uiAddr = sHighDevVAddr.uiAddr - 1;
 
-       
+       /* Update our PD flush mask if required */
        if (bFlushSystemCache)
        {
                MMU_CONTEXT *psMMUContext;
@@ -1137,7 +1585,7 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                                        psMMUContext->ui32PDChangeMask[i] |= ui32ModifiedCachelines[i];
                                }
 
-                               
+                               /* advance to next context */
                                psMMUContext = psMMUContext->psNext;
                        }
                }
@@ -1149,7 +1597,11 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
                        }
                }
 
-               
+               /*
+                * Always hook up the dummy page when we allocate a new range of PTs.
+                * It might be this is overwritten before the SGX access the dummy page
+                * but we don't care, it's a lot simpler to add this logic here.
+                */
                psMMUContext = pMMUHeap->psMMUContext;
                for (i=0;i<BRN31620_CACHE_FLUSH_INDEX_SIZE;i++)
                {
@@ -1165,7 +1617,7 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
 
                                        ui32PDIndex = (((i * BRN31620_CACHE_FLUSH_BITS_SIZE) + j) * BRN31620_PDES_PER_CACHE_LINE_SIZE) + BRN31620_DUMMY_PDE_INDEX;
 
-                                       
+                                       /* The PT for the dummy page might not be "live". If not get it from the saved pointer */
                                        if (psMMUContext->apsPTInfoList[ui32PDIndex])
                                        {
                                                psTempPTInfo = psMMUContext->apsPTInfoList[ui32PDIndex];
@@ -1177,13 +1629,14 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
 
                                        PVR_ASSERT(psTempPTInfo != IMG_NULL);
 
+                                       MakeKernelPageReadWrite(psTempPTInfo->PTPageCpuVAddr);
                                        pui32Tmp = (IMG_UINT32 *) psTempPTInfo->PTPageCpuVAddr;
                                        PVR_ASSERT(pui32Tmp != IMG_NULL);
                                        pui32Tmp[BRN31620_DUMMY_PTE_INDEX] = (psDevInfo->sBRN31620DummyPageDevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                                                                                        | SGX_MMU_PTE_DUMMY_PAGE
                                                                                                                        | SGX_MMU_PTE_READONLY
                                                                                                                        | SGX_MMU_PTE_VALID;
-
+                                       MakeKernelPageReadOnly(psTempPTInfo->PTPageCpuVAddr);
                                        PDUMPCOMMENT("BRN31620 Dump PTE for dummy page after wireing up new PT");
                                        PDUMPMEMPTENTRIES(&pMMUHeap->sMMUAttrib, psTempPTInfo->hPTPageOSMemHandle, (IMG_VOID *) &pui32Tmp[BRN31620_DUMMY_PTE_INDEX], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PT_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                                }
@@ -1197,20 +1650,44 @@ _DeferredAllocPagetables(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT
 
 
 #if defined(PDUMP)
+/*!
+ *     FUNCTION:       MMU_GetPDumpContextID
+ *
+ *     RETURNS:        pdump MMU context ID
+ */
 IMG_UINT32 MMU_GetPDumpContextID(IMG_HANDLE hDevMemContext)
 {
        BM_CONTEXT *pBMContext = hDevMemContext;
        PVR_ASSERT(pBMContext);
-        
+       /* PRQA S 0505 1 */ /* PVR_ASSERT should catch NULL ptr */
        return pBMContext->psMMUContext->ui32PDumpMMUContextID;
 }
 
+/*!
+ *     FUNCTION:       MMU_SetPDumpAttribs
+ *
+ *     PURPOSE:        Called from MMU_Initialise and MMU_Create.
+ *                             Sets up device-specific attributes for pdumping.
+ *                             FIXME: breaks variable size PTs. Really need separate per context
+ *                             and per heap attribs.
+ *
+ *     INPUT:          psDeviceNode - used to access deviceID
+ *     INPUT:          ui32DataPageMask - data page mask
+ *     INPUT:          ui32PTSize - PT size
+ *
+ *     OUTPUT:         psMMUAttrib - pdump MMU attributes
+ *
+ *     RETURNS:        none
+ */
+#if defined(SGX_FEATURE_VARIABLE_MMU_PAGE_SIZE)
+# error "FIXME: breaks variable size pagetables"
+#endif
 static IMG_VOID MMU_SetPDumpAttribs(PDUMP_MMU_ATTRIB *psMMUAttrib,
        PVRSRV_DEVICE_NODE *psDeviceNode,
        IMG_UINT32 ui32DataPageMask,
        IMG_UINT32 ui32PTSize)
 {
-       
+       /* Sets up device ID, contains pdump memspace name */
        psMMUAttrib->sDevId = psDeviceNode->sDevId;
        
        psMMUAttrib->pszPDRegRegion = IMG_NULL;
@@ -1223,8 +1700,18 @@ static IMG_VOID MMU_SetPDumpAttribs(PDUMP_MMU_ATTRIB *psMMUAttrib,
        psMMUAttrib->ui32PDEMask = SGX_MMU_PDE_ADDR_MASK;
        psMMUAttrib->ui32PDEAlignShift = SGX_MMU_PDE_ADDR_ALIGNSHIFT;
 }
-#endif 
+#endif /* PDUMP */
+
+/*!
+******************************************************************************
+       FUNCTION:   MMU_Initialise
 
+       PURPOSE:        Called from BM_CreateContext.
+                               Allocates the top level Page Directory 4k Page for the new context.
+
+       PARAMETERS: None
+       RETURNS:    PVRSRV_ERROR
+******************************************************************************/
 PVRSRV_ERROR
 MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, IMG_DEV_PHYADDR *psPDDevPAddr)
 {
@@ -1244,8 +1731,8 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
 
        SysAcquireData(&psSysData);
 #if defined(PDUMP)
-       
-       
+       /* Note: these attribs are on the stack, used only to pdump the MMU context
+        * creation. */
        MMU_SetPDumpAttribs(&sMMUAttrib, psDeviceNode,
                                                SGX_MMU_PAGE_MASK,
                                                SGX_MMU_PT_SIZE * sizeof(IMG_UINT32));
@@ -1262,21 +1749,24 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
        }
        OSMemSet (psMMUContext, 0, sizeof(MMU_CONTEXT));
 
-       
+       /* stick the devinfo in the context for subsequent use */
        psDevInfo = (PVRSRV_SGXDEV_INFO*)psDeviceNode->pvDevice;
        psMMUContext->psDevInfo = psDevInfo;
 
-       
+       /* record device node for subsequent use */
        psMMUContext->psDeviceNode = psDeviceNode;
 
-       
+       /* allocate 4k page directory page for the new context */
        if(psDeviceNode->psLocalDevMemArena == IMG_NULL)
        {
                if (OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                       SGX_MMU_PAGE_SIZE,
-                                                       SGX_MMU_PAGE_SIZE,
-                                                       &pvPDCpuVAddr,
-                                                       &hPDOSMemHandle) != PVRSRV_OK)
+                                                SGX_MMU_PAGE_SIZE,
+                                                SGX_MMU_PAGE_SIZE,
+                                                IMG_NULL,
+                                                0,
+                                                IMG_NULL,
+                                                &pvPDCpuVAddr,
+                                                &hPDOSMemHandle) != PVRSRV_OK)
                {
                        PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to OSAllocPages failed"));
                        return PVRSRV_ERROR_FAILED_TO_ALLOC_PAGES;
@@ -1289,7 +1779,8 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                }
                else
                {
-                       
+                       /* This is not used in all cases, since not all ports currently
+                        * support OSMemHandleToCpuPAddr */
                        sCpuPAddr = OSMemHandleToCpuPAddr(hPDOSMemHandle, 0);
                }
                sPDDevPAddr = SysCpuPAddrToDevPAddr (PVRSRV_DEVICE_TYPE_SGX, sCpuPAddr);
@@ -1299,15 +1790,18 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                #endif
 
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-               
+               /* Allocate dummy PT and Data pages for the first context to be created */
                if(!psDevInfo->pvMMUContextList)
                {
-                       
+                       /* Dummy PT page */
                        if (OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                               SGX_MMU_PAGE_SIZE,
-                                                               SGX_MMU_PAGE_SIZE,
-                                                               &psDevInfo->pvDummyPTPageCpuVAddr,
-                                                               &psDevInfo->hDummyPTPageOSMemHandle) != PVRSRV_OK)
+                                                        SGX_MMU_PAGE_SIZE,
+                                                        SGX_MMU_PAGE_SIZE,
+                                                        IMG_NULL,
+                                                        0,
+                                                        IMG_NULL,
+                                                        &psDevInfo->pvDummyPTPageCpuVAddr,
+                                                        &psDevInfo->hDummyPTPageOSMemHandle) != PVRSRV_OK)
                        {
                                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to OSAllocPages failed"));
                                return PVRSRV_ERROR_FAILED_TO_ALLOC_PAGES;
@@ -1320,17 +1814,21 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                        }
                        else
                        {
-                               
+                               /* This is not used in all cases, since not all ports currently
+                                * support OSMemHandleToCpuPAddr */
                                sCpuPAddr = OSMemHandleToCpuPAddr(psDevInfo->hDummyPTPageOSMemHandle, 0);
                        }
                        psDevInfo->sDummyPTDevPAddr = SysCpuPAddrToDevPAddr (PVRSRV_DEVICE_TYPE_SGX, sCpuPAddr);
 
-                       
+                       /* Dummy Data page */
                        if (OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                               SGX_MMU_PAGE_SIZE,
-                                                               SGX_MMU_PAGE_SIZE,
-                                                               &psDevInfo->pvDummyDataPageCpuVAddr,
-                                                               &psDevInfo->hDummyDataPageOSMemHandle) != PVRSRV_OK)
+                                                        SGX_MMU_PAGE_SIZE,
+                                                        SGX_MMU_PAGE_SIZE,
+                                                        IMG_NULL,
+                                                        0,
+                                                        IMG_NULL,
+                                                        &psDevInfo->pvDummyDataPageCpuVAddr,
+                                                        &psDevInfo->hDummyDataPageOSMemHandle) != PVRSRV_OK)
                        {
                                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to OSAllocPages failed"));
                                return PVRSRV_ERROR_FAILED_TO_ALLOC_PAGES;
@@ -1347,24 +1845,27 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                        }
                        psDevInfo->sDummyDataDevPAddr = SysCpuPAddrToDevPAddr (PVRSRV_DEVICE_TYPE_SGX, sCpuPAddr);
                }
-#endif 
+#endif /* #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE) */
 #if defined(FIX_HW_BRN_31620)
-               
+               /* Allocate dummy Data pages for the first context to be created */
                if(!psDevInfo->pvMMUContextList)
                {
                        IMG_UINT32 j;
-                       
+                       /* Allocate dummy page */
                        if (OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                               SGX_MMU_PAGE_SIZE,
-                                                               SGX_MMU_PAGE_SIZE,
-                                                               &psDevInfo->pvBRN31620DummyPageCpuVAddr,
-                                                               &psDevInfo->hBRN31620DummyPageOSMemHandle) != PVRSRV_OK)
+                                                        SGX_MMU_PAGE_SIZE,
+                                                        SGX_MMU_PAGE_SIZE,
+                                                        IMG_NULL,
+                                                        0,
+                                                        IMG_NULL,
+                                                        &psDevInfo->pvBRN31620DummyPageCpuVAddr,
+                                                        &psDevInfo->hBRN31620DummyPageOSMemHandle) != PVRSRV_OK)
                        {
                                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to OSAllocPages failed"));
                                return PVRSRV_ERROR_FAILED_TO_ALLOC_PAGES;
                        }                               
 
-                       
+                       /* Get a physical address */
                        if(psDevInfo->pvBRN31620DummyPageCpuVAddr)
                        {
                                sCpuPAddr = OSMapLinToCPUPhys(psDevInfo->hBRN31620DummyPageOSMemHandle,
@@ -1384,18 +1885,21 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                        psDevInfo->sBRN31620DummyPageDevPAddr = SysCpuPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sCpuPAddr);
                        PDUMPMALLOCPAGETABLE(&psDeviceNode->sDevId, psDevInfo->hBRN31620DummyPageOSMemHandle, 0, psDevInfo->pvBRN31620DummyPageCpuVAddr, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
 
-                       
+                       /* Allocate dummy PT */
                        if (OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                               SGX_MMU_PAGE_SIZE,
-                                                               SGX_MMU_PAGE_SIZE,
-                                                               &psDevInfo->pvBRN31620DummyPTCpuVAddr,
-                                                               &psDevInfo->hBRN31620DummyPTOSMemHandle) != PVRSRV_OK)
+                                                        SGX_MMU_PAGE_SIZE,
+                                                        SGX_MMU_PAGE_SIZE,
+                                                        IMG_NULL,
+                                                        0,
+                                                        IMG_NULL,
+                                                        &psDevInfo->pvBRN31620DummyPTCpuVAddr,
+                                                        &psDevInfo->hBRN31620DummyPTOSMemHandle) != PVRSRV_OK)
                        {
                                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to OSAllocPages failed"));
                                return PVRSRV_ERROR_FAILED_TO_ALLOC_PAGES;
                        }                               
 
-                       
+                       /* Get a physical address */
                        if(psDevInfo->pvBRN31620DummyPTCpuVAddr)
                        {
                                sCpuPAddr = OSMapLinToCPUPhys(psDevInfo->hBRN31620DummyPTOSMemHandle,
@@ -1416,7 +1920,7 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
        {
                IMG_SYS_PHYADDR sSysPAddr;
 
-               
+               /* allocate from the device's local memory arena */
                if(RA_Alloc(psDeviceNode->psLocalDevMemArena,
                                        SGX_MMU_PAGE_SIZE,
                                        IMG_NULL,
@@ -1424,13 +1928,15 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                                        0,
                                        SGX_MMU_PAGE_SIZE,
                                        0,
+                                       IMG_NULL,
+                                       0,
                                        &(sSysPAddr.uiAddr))!= IMG_TRUE)
                {
                        PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to RA_Alloc failed"));
                        return PVRSRV_ERROR_FAILED_TO_ALLOC_VIRT_MEMORY;
                }
 
-               
+               /* derive the CPU virtual address */
                sCpuPAddr = SysSysPAddrToCpuPAddr(sSysPAddr);
                sPDDevPAddr = SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sSysPAddr);
                pvPDCpuVAddr = OSMapPhysToLin(sCpuPAddr,
@@ -1448,10 +1954,10 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                #endif
 
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-               
+               /* Allocate dummy PT and Data pages for the first context to be created */
                if(!psDevInfo->pvMMUContextList)
                {
-                       
+                       /* Dummy PT page */
                        if(RA_Alloc(psDeviceNode->psLocalDevMemArena,
                                                SGX_MMU_PAGE_SIZE,
                                                IMG_NULL,
@@ -1459,13 +1965,15 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                                                0,
                                                SGX_MMU_PAGE_SIZE,
                                                0,
+                                               IMG_NULL,
+                                               0,
                                                &(sSysPAddr.uiAddr))!= IMG_TRUE)
                        {
                                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to RA_Alloc failed"));
                                return PVRSRV_ERROR_FAILED_TO_ALLOC_VIRT_MEMORY;
                        }
 
-                       
+                       /* derive the CPU virtual address */
                        sCpuPAddr = SysSysPAddrToCpuPAddr(sSysPAddr);
                        psDevInfo->sDummyPTDevPAddr = SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sSysPAddr);
                        psDevInfo->pvDummyPTPageCpuVAddr = OSMapPhysToLin(sCpuPAddr,
@@ -1478,7 +1986,7 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                                return PVRSRV_ERROR_FAILED_TO_MAP_PAGE_TABLE;
                        }
 
-                       
+                       /* Dummy Data page */
                        if(RA_Alloc(psDeviceNode->psLocalDevMemArena,
                                                SGX_MMU_PAGE_SIZE,
                                                IMG_NULL,
@@ -1486,13 +1994,15 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                                                0,
                                                SGX_MMU_PAGE_SIZE,
                                                0,
+                                               IMG_NULL,
+                                               0,
                                                &(sSysPAddr.uiAddr))!= IMG_TRUE)
                        {
                                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to RA_Alloc failed"));
                                return PVRSRV_ERROR_FAILED_TO_ALLOC_VIRT_MEMORY;
                        }
 
-                       
+                       /* derive the CPU virtual address */
                        sCpuPAddr = SysSysPAddrToCpuPAddr(sSysPAddr);
                        psDevInfo->sDummyDataDevPAddr = SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sSysPAddr);
                        psDevInfo->pvDummyDataPageCpuVAddr = OSMapPhysToLin(sCpuPAddr,
@@ -1505,13 +2015,13 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                                return PVRSRV_ERROR_FAILED_TO_MAP_PAGE_TABLE;
                        }
                }
-#endif 
+#endif /* #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE) */
 #if defined(FIX_HW_BRN_31620)
-               
+               /* Allocate dummy PT and Data pages for the first context to be created */
                if(!psDevInfo->pvMMUContextList)
                {
                        IMG_UINT32 j;
-                       
+                       /* Allocate dummy page */
                        if(RA_Alloc(psDeviceNode->psLocalDevMemArena,
                                                SGX_MMU_PAGE_SIZE,
                                                IMG_NULL,
@@ -1519,13 +2029,15 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                                                0,
                                                SGX_MMU_PAGE_SIZE,
                                                0,
+                                               IMG_NULL,
+                                               0,
                                                &(sSysPAddr.uiAddr))!= IMG_TRUE)
                        {
                                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to RA_Alloc failed"));
                                return PVRSRV_ERROR_FAILED_TO_ALLOC_VIRT_MEMORY;
                        }
 
-                       
+                       /* derive the CPU virtual address */
                        sCpuPAddr = SysSysPAddrToCpuPAddr(sSysPAddr);
                        psDevInfo->sBRN31620DummyPageDevPAddr = SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sSysPAddr);
                        psDevInfo->pvBRN31620DummyPageCpuVAddr = OSMapPhysToLin(sCpuPAddr,
@@ -1538,14 +2050,16 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                                return PVRSRV_ERROR_FAILED_TO_MAP_PAGE_TABLE;
                        }
 
+                       MakeKernelPageReadWrite(psDevInfo->pvBRN31620DummyPageCpuVAddr);
                        pui32Tmp = (IMG_UINT32 *)psDevInfo->pvBRN31620DummyPageCpuVAddr;
                        for(j=0; j<(SGX_MMU_PAGE_SIZE/4); j++)
                        {
                                pui32Tmp[j] = BRN31620_DUMMY_PAGE_SIGNATURE;
                        }
+                       MakeKernelPageReadOnly(psDevInfo->pvBRN31620DummyPageCpuVAddr);
                        PDUMPMALLOCPAGETABLE(&psDeviceNode->sDevId, psDevInfo->hBRN31620DummyPageOSMemHandle, 0, psDevInfo->pvBRN31620DummyPageCpuVAddr, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
 
-                       
+                       /* Allocate dummy PT */
                        if(RA_Alloc(psDeviceNode->psLocalDevMemArena,
                                                SGX_MMU_PAGE_SIZE,
                                                IMG_NULL,
@@ -1553,13 +2067,15 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                                                0,
                                                SGX_MMU_PAGE_SIZE,
                                                0,
+                                               IMG_NULL,
+                                               0,
                                                &(sSysPAddr.uiAddr))!= IMG_TRUE)
                        {
                                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: ERROR call to RA_Alloc failed"));
                                return PVRSRV_ERROR_FAILED_TO_ALLOC_VIRT_MEMORY;
                        }
 
-                       
+                       /* derive the CPU virtual address */
                        sCpuPAddr = SysSysPAddrToCpuPAddr(sSysPAddr);
                        psDevInfo->sBRN31620DummyPTDevPAddr = SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sSysPAddr);
                        psDevInfo->pvBRN31620DummyPTCpuVAddr = OSMapPhysToLin(sCpuPAddr,
@@ -1576,13 +2092,13 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                        OSMemSet(psDevInfo->pvBRN31620DummyPTCpuVAddr,0,SGX_MMU_PAGE_SIZE);             
                        PDUMPMALLOCPAGETABLE(&psDeviceNode->sDevId, psDevInfo->hBRN31620DummyPTOSMemHandle, 0, psDevInfo->pvBRN31620DummyPTCpuVAddr, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
                }
-#endif 
+#endif /* #if defined(FIX_HW_BRN_31620) */
        }
 
 #if defined(FIX_HW_BRN_31620)
        if (!psDevInfo->pvMMUContextList)
        {
-               
+               /* Save the kernel MMU context which is always the 1st to be created */
                psDevInfo->hKernelMMUContext = psMMUContext;
                PVR_DPF((PVR_DBG_ERROR, "MMU_Initialise: saving kernel mmu context: %p", psMMUContext));
        }
@@ -1590,12 +2106,14 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
 
 #if defined(PDUMP)
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-       
+       /* Find out if this context is for the active pdump client.
+        * If it is, need to ensure PD entries are pdumped whenever another
+        * process allocates from a shared heap. */
        {
                PVRSRV_PER_PROCESS_DATA* psPerProc = PVRSRVFindPerProcessData();
                if(psPerProc == IMG_NULL)
                {
-                       
+                       /* changes to the kernel context PD/PTs should be pdumped */
                        psMMUContext->bPDumpActive = IMG_TRUE;
                }
                else
@@ -1603,8 +2121,8 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                        psMMUContext->bPDumpActive = psPerProc->bPDumpActive;
                }
        }
-#endif 
-       
+#endif /* SUPPORT_PDUMP_MULTI_PROCESS */
+       /* pdump the PD malloc */
 #if IMG_ADDRSPACE_PHYSADDR_BITS == 32
        PDUMPCOMMENT("Alloc page directory for new MMU context (PDDevPAddr == 0x%08x)",
                        sPDDevPAddr.uiAddr);
@@ -1613,7 +2131,7 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                        sPDDevPAddr.uiHighAddr, sPDDevPAddr.uiAddr);
 #endif
        PDUMPMALLOCPAGETABLE(&psDeviceNode->sDevId, hPDOSMemHandle, 0, pvPDCpuVAddr, SGX_MMU_PAGE_SIZE, 0, PDUMP_PD_UNIQUETAG);
-#endif 
+#endif /* PDUMP */
 
 #ifdef SUPPORT_SGX_MMU_BYPASS
        EnableHostAccess(psMMUContext);
@@ -1631,55 +2149,65 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
 
 
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-       
+       MakeKernelPageReadWrite(pvPDCpuVAddr);
+       /*  wire-up the new PD to the dummy PT */
        for(i=0; i<SGX_MMU_PD_SIZE; i++)
        {
                pui32Tmp[i] = (psDevInfo->sDummyPTDevPAddr.uiAddr>>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                        | SGX_MMU_PDE_PAGE_SIZE_4K
                                        | SGX_MMU_PDE_VALID;
        }
+       MakeKernelPageReadOnly(pvPDCpuVAddr);
 
        if(!psDevInfo->pvMMUContextList)
        {
-               
-
-
+               /*
+                       if we've just allocated the dummy pages
+                       wire up the dummy PT to the dummy data page
+               */
+               MakeKernelPageReadWrite(psDevInfo->pvDummyPTPageCpuVAddr);
                pui32Tmp = (IMG_UINT32 *)psDevInfo->pvDummyPTPageCpuVAddr;
                for(i=0; i<SGX_MMU_PT_SIZE; i++)
                {
                        pui32Tmp[i] = (psDevInfo->sDummyDataDevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                | SGX_MMU_PTE_VALID;
                }
-               
+               MakeKernelPageReadOnly(psDevInfo->pvDummyPTPageCpuVAddr);
+               /* pdump the Dummy PT Page */
                PDUMPCOMMENT("Dummy Page table contents");
                PDUMPMEMPTENTRIES(&sMMUAttrib, psDevInfo->hDummyPTOSMemHandle, psDevInfo->pvDummyPTPageCpuVAddr, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
 
-               
-
+               /*
+                       write a signature to the dummy data page
+               */
+               MakeKernelPageReadWrite(psDevInfo->pvDummyDataPageCpuVAddr);
                pui32Tmp = (IMG_UINT32 *)psDevInfo->pvDummyDataPageCpuVAddr;
                for(i=0; i<(SGX_MMU_PAGE_SIZE/4); i++)
                {
                        pui32Tmp[i] = DUMMY_DATA_PAGE_SIGNATURE;
                }
-               
+               MakeKernelPageReadOnly(psDevInfo->pvDummyDataPageCpuVAddr);
+               /* pdump the Dummy Data Page */
                PDUMPCOMMENT("Dummy Data Page contents");
                PDUMPMEMPTENTRIES(PVRSRV_DEVICE_TYPE_SGX, psDevInfo->hDummyDataPageOSMemHandle, psDevInfo->pvDummyDataPageCpuVAddr, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
        }
-#else 
-       
+#else /* #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE) */
+       /* initialise the PD to invalid address state */
+       MakeKernelPageReadWrite(pvPDCpuVAddr);
        for(i=0; i<SGX_MMU_PD_SIZE; i++)
        {
-               
+               /* invalid, no read, no write, no cache consistency */
                pui32Tmp[i] = 0;
        }
-#endif 
+       MakeKernelPageReadOnly(pvPDCpuVAddr);
+#endif /* #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE) */
 
 #if defined(PDUMP)
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
        if(psMMUContext->bPDumpActive)
-#endif 
+#endif /* SUPPORT_PDUMP_MULTI_PROCESS */
        {
-               
+               /* pdump the PD Page */
                PDUMPCOMMENT("Page directory contents");
                PDUMPPDENTRIES(&sMMUAttrib, hPDOSMemHandle, pvPDCpuVAddr, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
        }
@@ -1693,59 +2221,62 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
 
                PDUMPCOMMENT("BRN31620 Set up dummy PT");
 
+               MakeKernelPageReadWrite(psDevInfo->pvBRN31620DummyPTCpuVAddr);
                pui32PT = (IMG_UINT32 *) psDevInfo->pvBRN31620DummyPTCpuVAddr;
                pui32PT[BRN31620_DUMMY_PTE_INDEX] = (psDevInfo->sBRN31620DummyPageDevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                                | SGX_MMU_PTE_DUMMY_PAGE
                                                                | SGX_MMU_PTE_READONLY
                                                                | SGX_MMU_PTE_VALID;
-
+               MakeKernelPageReadOnly(psDevInfo->pvBRN31620DummyPTCpuVAddr);
 
 #if defined(PDUMP)
-               
+               /* Dump initial contents */
                PDUMPCOMMENT("BRN31620 Dump dummy PT contents");
                PDUMPMEMPTENTRIES(&sMMUAttrib,  psDevInfo->hBRN31620DummyPTOSMemHandle, psDevInfo->pvBRN31620DummyPTCpuVAddr, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                PDUMPCOMMENT("BRN31620 Dump dummy page contents");
                PDUMPMEMPTENTRIES(&sMMUAttrib,  psDevInfo->hBRN31620DummyPageOSMemHandle, psDevInfo->pvBRN31620DummyPageCpuVAddr, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
 
-                               
+               /* Dump the wiring */           
                for(i=0;i<SGX_MMU_PT_SIZE;i++)
                {
                        PDUMPMEMPTENTRIES(&sMMUAttrib, psDevInfo->hBRN31620DummyPTOSMemHandle, &pui32PT[i], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                }
 #endif
                PDUMPCOMMENT("BRN31620 Dump PDE wire up");
-               
+               /* Walk the PD wireing up the PT's */
                for(i=0;i<SGX_MMU_PD_SIZE;i++)
                {
                        pui32Tmp[i] = 0;
 
                        if (ui32PDCount == BRN31620_DUMMY_PDE_INDEX)
                        {
+                               MakeKernelPageReadWrite(pvPDCpuVAddr);
                                pui32Tmp[i] = (psDevInfo->sBRN31620DummyPTDevPAddr.uiAddr>>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                                | SGX_MMU_PDE_PAGE_SIZE_4K
                                                | SGX_MMU_PDE_DUMMY_PAGE
                                                | SGX_MMU_PDE_VALID;
+                               MakeKernelPageReadOnly(pvPDCpuVAddr);
                        }
                                PDUMPMEMPTENTRIES(&sMMUAttrib, hPDOSMemHandle, (IMG_VOID *) &pui32Tmp[i], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PT_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                        ui32PDCount++;
                        if (ui32PDCount == BRN31620_PDES_PER_CACHE_LINE_SIZE)
                        {
-                               
+                               /* Reset PT count */
                                ui32PDCount = 0;
                        }
                }
 
 
-               
+               /* pdump the Dummy PT Page */
                PDUMPCOMMENT("BRN31620 dummy Page table contents");
                PDUMPMEMPTENTRIES(&sMMUAttrib, psDevInfo->hBRN31620DummyPageOSMemHandle, psDevInfo->pvBRN31620DummyPageCpuVAddr, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
        }
 #endif
 #if defined(PDUMP)
-       
+       /* pdump set MMU context */
        {
                PVRSRV_ERROR eError;
-               
+               /* default MMU type is 1, 4k page */
                IMG_UINT32 ui32MMUType = 1;
 
                #if defined(SGX_FEATURE_36BIT_MMU)
@@ -1770,7 +2301,7 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                }
        }
 
-       
+       /* PDump the context ID */
        PDUMPCOMMENT("Set MMU context complete (MMU Context ID == %u)", psMMUContext->ui32PDumpMMUContextID);
 #endif
 
@@ -1790,18 +2321,24 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
                psMMUContext->apsPTInfoListSave[i] = IMG_NULL;
        }
 #endif
-       
+       /* store PD info in the MMU context */
        psMMUContext->pvPDCpuVAddr = pvPDCpuVAddr;
        psMMUContext->sPDDevPAddr = sPDDevPAddr;
        psMMUContext->hPDOSMemHandle = hPDOSMemHandle;
 
-       
+       /* Get some process information to aid debug */
+       psMMUContext->ui32PID = OSGetCurrentProcessIDKM();
+       psMMUContext->szName[0] = '\0';
+       OSGetCurrentProcessNameKM(psMMUContext->szName, MMU_CONTEXT_NAME_SIZE);
+
+       /* return context */
        *ppsMMUContext = psMMUContext;
 
-       
+       /* return the PD DevVAddr */
        *psPDDevPAddr = sPDDevPAddr;
 
-       
+
+       /* add the new MMU context onto the list of MMU contexts */
        psMMUContext->psNext = (MMU_CONTEXT*)psDevInfo->pvMMUContextList;
        psDevInfo->pvMMUContextList = (IMG_VOID*)psMMUContext;
 
@@ -1812,6 +2349,15 @@ MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, I
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_Finalise
+
+       PURPOSE:    Finalise the mmu module, deallocate all resources.
+
+       PARAMETERS: In: psMMUContext - MMU context to deallocate
+       RETURNS:    None.
+******************************************************************************/
 IMG_VOID
 MMU_Finalise (MMU_CONTEXT *psMMUContext)
 {
@@ -1826,11 +2372,11 @@ MMU_Finalise (MMU_CONTEXT *psMMUContext)
        SysAcquireData(&psSysData);
 
 #if defined(PDUMP)
-       
+       /* pdump the MMU context clear */
        PDUMPCOMMENT("Clear MMU context (MMU Context ID == %u)", psMMUContext->ui32PDumpMMUContextID);
        PDUMPCLEARMMUCONTEXT(PVRSRV_DEVICE_TYPE_SGX, psMMUContext->psDeviceNode->sDevId.pszPDumpDevName, psMMUContext->ui32PDumpMMUContextID, 2);
 
-       
+       /* pdump the PD free */
 #if IMG_ADDRSPACE_PHYSADDR_BITS == 32
        PDUMPCOMMENT("Free page directory (PDDevPAddr == 0x%08x)",
                        psMMUContext->sPDDevPAddr.uiAddr);
@@ -1838,7 +2384,7 @@ MMU_Finalise (MMU_CONTEXT *psMMUContext)
        PDUMPCOMMENT("Free page directory, 64-bit arch detected (PDDevPAddr == 0x%08x%08x)",
                        psMMUContext->sPDDevPAddr.uiHighAddr, psMMUContext->sPDDevPAddr.uiAddr);
 #endif
-#endif 
+#endif /* PDUMP */
 
        PDUMPFREEPAGETABLE(&psMMUContext->psDeviceNode->sDevId, psMMUContext->hPDOSMemHandle, psMMUContext->pvPDCpuVAddr, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
@@ -1848,29 +2394,33 @@ MMU_Finalise (MMU_CONTEXT *psMMUContext)
 
        pui32Tmp = (IMG_UINT32 *)psMMUContext->pvPDCpuVAddr;
 
-       
+       MakeKernelPageReadWrite(psMMUContext->pvPDCpuVAddr);
+       /* initialise the PD to invalid address state */
        for(i=0; i<SGX_MMU_PD_SIZE; i++)
        {
-               
+               /* invalid, no read, no write, no cache consistency */
                pui32Tmp[i] = 0;
        }
+       MakeKernelPageReadOnly(psMMUContext->pvPDCpuVAddr);
 
-       
-
-
-
+       /*
+               free the PD:
+               depending on the specific system, the PD is allocated from system memory
+               or device local memory.  For now, just look for at least a valid local heap/arena
+       */
        if(psMMUContext->psDeviceNode->psLocalDevMemArena == IMG_NULL)
        {
 #if defined(FIX_HW_BRN_31620)
                PVRSRV_SGXDEV_INFO *psDevInfo = (PVRSRV_SGXDEV_INFO*)psMMUContext->psDevInfo;
 #endif
+               MakeKernelPageReadWrite(psMMUContext->pvPDCpuVAddr);
                OSFreePages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
                                                SGX_MMU_PAGE_SIZE,
                                                psMMUContext->pvPDCpuVAddr,
                                                psMMUContext->hPDOSMemHandle);
 
 #if defined(FIX_HW_BRN_31620)
-               
+               /* If this is the _last_ MMU context it must be the uKernel */
                if (!psMMUContextList->psNext)
                {
                        PDUMPFREEPAGETABLE(&psMMUContext->psDeviceNode->sDevId, psDevInfo->hBRN31620DummyPageOSMemHandle, psDevInfo->pvBRN31620DummyPageCpuVAddr, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
@@ -1888,7 +2438,7 @@ MMU_Finalise (MMU_CONTEXT *psMMUContext)
                }
 #endif
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-               
+               /* if this is the last context free the dummy pages too */
                if(!psMMUContextList->psNext)
                {
                        OSFreePages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
@@ -1907,82 +2457,82 @@ MMU_Finalise (MMU_CONTEXT *psMMUContext)
                IMG_SYS_PHYADDR sSysPAddr;
                IMG_CPU_PHYADDR sCpuPAddr;
 
-               
+               /*  derive the system physical address */
                sCpuPAddr = OSMapLinToCPUPhys(psMMUContext->hPDOSMemHandle,
                                                                          psMMUContext->pvPDCpuVAddr);
                sSysPAddr = SysCpuPAddrToSysPAddr(sCpuPAddr);
 
-               
+               /* unmap the CPU mapping */
                OSUnMapPhysToLin(psMMUContext->pvPDCpuVAddr,
                                                        SGX_MMU_PAGE_SIZE,
                             PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
                                                        psMMUContext->hPDOSMemHandle);
-               
+               /* and free the memory */
                RA_Free (psMMUContext->psDeviceNode->psLocalDevMemArena, sSysPAddr.uiAddr, IMG_FALSE);
 
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-               
+               /* if this is the last context free the dummy pages too */
                if(!psMMUContextList->psNext)
                {
-                       
+                       /* free the Dummy PT Page */
                        sCpuPAddr = OSMapLinToCPUPhys(psDevInfo->hDummyPTPageOSMemHandle,
                                                                                  psDevInfo->pvDummyPTPageCpuVAddr);
                        sSysPAddr = SysCpuPAddrToSysPAddr(sCpuPAddr);
 
-                       
+                       /* unmap the CPU mapping */
                        OSUnMapPhysToLin(psDevInfo->pvDummyPTPageCpuVAddr,
                                                                SGX_MMU_PAGE_SIZE,
                                 PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
                                                                psDevInfo->hDummyPTPageOSMemHandle);
-                       
+                       /* and free the memory */
                        RA_Free (psMMUContext->psDeviceNode->psLocalDevMemArena, sSysPAddr.uiAddr, IMG_FALSE);
 
-                       
+                       /* free the Dummy Data Page */
                        sCpuPAddr = OSMapLinToCPUPhys(psDevInfo->hDummyDataPageOSMemHandle,
                                                                                  psDevInfo->pvDummyDataPageCpuVAddr);
                        sSysPAddr = SysCpuPAddrToSysPAddr(sCpuPAddr);
 
-                       
+                       /* unmap the CPU mapping */
                        OSUnMapPhysToLin(psDevInfo->pvDummyDataPageCpuVAddr,
                                                                SGX_MMU_PAGE_SIZE,
                                 PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
                                                                psDevInfo->hDummyDataPageOSMemHandle);
-                       
+                       /* and free the memory */
                        RA_Free (psMMUContext->psDeviceNode->psLocalDevMemArena, sSysPAddr.uiAddr, IMG_FALSE);
                }
 #endif
 #if defined(FIX_HW_BRN_31620)
-               
+               /* if this is the last context free the dummy pages too */
                if(!psMMUContextList->psNext)
                {
-                       
+                       /* free the Page */
                        PDUMPFREEPAGETABLE(&psMMUContext->psDeviceNode->sDevId, psDevInfo->hBRN31620DummyPageOSMemHandle, psDevInfo->pvBRN31620DummyPageCpuVAddr, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
 
                        sCpuPAddr = OSMapLinToCPUPhys(psDevInfo->hBRN31620DummyPageOSMemHandle,
                                                                                  psDevInfo->pvBRN31620DummyPageCpuVAddr);
                        sSysPAddr = SysCpuPAddrToSysPAddr(sCpuPAddr);
 
-                       
+                       /* unmap the CPU mapping */
                        OSUnMapPhysToLin(psDevInfo->pvBRN31620DummyPageCpuVAddr,
                                                                SGX_MMU_PAGE_SIZE,
                                 PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
                                                                psDevInfo->hBRN31620DummyPageOSMemHandle);
-                       
+                       /* and free the memory */
                        RA_Free (psMMUContext->psDeviceNode->psLocalDevMemArena, sSysPAddr.uiAddr, IMG_FALSE);
 
-                       
+                       /* free the Dummy PT */
                        PDUMPFREEPAGETABLE(&psMMUContext->psDeviceNode->sDevId, psDevInfo->hBRN31620DummyPTOSMemHandle, psDevInfo->pvBRN31620DummyPTCpuVAddr, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
 
                        sCpuPAddr = OSMapLinToCPUPhys(psDevInfo->hBRN31620DummyPTOSMemHandle,
                                                                                  psDevInfo->pvBRN31620DummyPTCpuVAddr);
                        sSysPAddr = SysCpuPAddrToSysPAddr(sCpuPAddr);
 
-                       
+                       /* unmap the CPU mapping */
                        OSUnMapPhysToLin(psDevInfo->pvBRN31620DummyPTCpuVAddr,
                                                                SGX_MMU_PAGE_SIZE,
                                 PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
                                                                psDevInfo->hBRN31620DummyPTOSMemHandle);
-                       
+                       /* and free the memory */
                        RA_Free (psMMUContext->psDeviceNode->psLocalDevMemArena, sSysPAddr.uiAddr, IMG_FALSE);
                }
 #endif
@@ -1990,27 +2540,38 @@ MMU_Finalise (MMU_CONTEXT *psMMUContext)
 
        PVR_DPF ((PVR_DBG_MESSAGE, "MMU_Finalise"));
 
-       
+       /* remove the MMU context from the list of MMU contexts */
        ppsMMUContext = (MMU_CONTEXT**)&psMMUContext->psDevInfo->pvMMUContextList;
        while(*ppsMMUContext)
        {
                if(*ppsMMUContext == psMMUContext)
                {
-                       
+                       /* remove item from the list */
                        *ppsMMUContext = psMMUContext->psNext;
                        break;
                }
 
-               
+               /* advance to next next */
                ppsMMUContext = &((*ppsMMUContext)->psNext);
        }
 
-       
+       /* free the context itself. */
        OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(MMU_CONTEXT), psMMUContext, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_InsertHeap
+
+       PURPOSE:    Copies PDEs from shared/exported heap into current MMU context.
+
+       PARAMETERS:     In:  psMMUContext - the mmu
+                   In:  psMMUHeap - a shared/exported heap
+
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID
 MMU_InsertHeap(MMU_CONTEXT *psMMUContext, MMU_HEAP *psMMUHeap)
 {
@@ -2021,20 +2582,21 @@ MMU_InsertHeap(MMU_CONTEXT *psMMUContext, MMU_HEAP *psMMUHeap)
        IMG_BOOL bInvalidateDirectoryCache = IMG_FALSE;
 #endif
 
-       
+       /* advance to the first entry */
        pui32PDCpuVAddr += psMMUHeap->psDevArena->BaseDevVAddr.uiAddr >> psMMUHeap->ui32PDShift;
        pui32KernelPDCpuVAddr += psMMUHeap->psDevArena->BaseDevVAddr.uiAddr >> psMMUHeap->ui32PDShift;
 
-       
-
-
+       /*
+               update the PD range relating to the heap's
+               device virtual address range
+       */
 #if defined(PDUMP)
        PDUMPCOMMENT("Page directory shared heap range copy");
        PDUMPCOMMENT("  (Source heap MMU Context ID == %u, PT count == 0x%x)",
                        psMMUHeap->psMMUContext->ui32PDumpMMUContextID,
                        psMMUHeap->ui32PageTableCount);
        PDUMPCOMMENT("  (Destination MMU Context ID == %u)", psMMUContext->ui32PDumpMMUContextID);
-#endif 
+#endif /* PDUMP */
 #ifdef SUPPORT_SGX_MMU_BYPASS
        EnableHostAccess(psMMUContext);
 #endif
@@ -2042,20 +2604,29 @@ MMU_InsertHeap(MMU_CONTEXT *psMMUContext, MMU_HEAP *psMMUHeap)
        for (ui32PDEntry = 0; ui32PDEntry < psMMUHeap->ui32PageTableCount; ui32PDEntry++)
        {
 #if (!defined(SUPPORT_SGX_MMU_DUMMY_PAGE)) && (!defined(FIX_HW_BRN_31620))
-               
+               /* check we have invalidated target PDEs */
                PVR_ASSERT(pui32PDCpuVAddr[ui32PDEntry] == 0);
 #endif
-
-               
+               MakeKernelPageReadWrite(psMMUContext->pvPDCpuVAddr);
+               /* copy over the PDEs */
                pui32PDCpuVAddr[ui32PDEntry] = pui32KernelPDCpuVAddr[ui32PDEntry];
+               MakeKernelPageReadOnly(psMMUContext->pvPDCpuVAddr);
                if (pui32PDCpuVAddr[ui32PDEntry])
                {
-                       
+                       /* Ensure the shared heap allocation is mapped into the context/PD
+                        * for the active pdump process/app. The PTs and backing physical
+                        * should also be pdumped (elsewhere).
+                        *              MALLOC (PT)
+                        *              LDB (init PT)
+                        *              MALLOC (data page)
+                        *              WRW (PTE->data page)
+                        *              LDB (init data page) -- could be useful to ensure page is initialised
+                        */
                #if defined(PDUMP)
-                       
+                       //PDUMPCOMMENT("MMU_InsertHeap: Mapping shared heap to new context %d (%s)", psMMUContext->ui32PDumpMMUContextID, (psMMUContext->bPDumpActive) ? "active" : "");
                #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
                        if(psMMUContext->bPDumpActive)
-               #endif 
+               #endif /* SUPPORT_PDUMP_MULTI_PROCESS */
                        {
                                PDUMPPDENTRIES(&psMMUHeap->sMMUAttrib, psMMUContext->hPDOSMemHandle, (IMG_VOID *) &pui32PDCpuVAddr[ui32PDEntry], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
                        }
@@ -2073,16 +2644,30 @@ MMU_InsertHeap(MMU_CONTEXT *psMMUContext, MMU_HEAP *psMMUHeap)
 #if !defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS)
        if (bInvalidateDirectoryCache)
        {
-               
-
-
-
+               /* This is actually not to do with multiple mem contexts, but to do with the directory cache.
+                       In the 1 context implementation of the MMU, the directory "cache" is actually a copy of the
+                       page directory memory, and requires updating whenever the page directory changes, even if there
+                       was no previous value in a particular entry
+               */
                MMU_InvalidateDirectoryCache(psMMUContext->psDevInfo);
        }
 #endif
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_UnmapPagesAndFreePTs
+
+       PURPOSE:    unmap pages, invalidate virtual address and try to free the PTs
+
+       PARAMETERS:     In:  psMMUHeap - the mmu.
+                   In:  sDevVAddr - the device virtual address.
+                   In:  ui32PageCount - page count
+                   In:  hUniqueTag - A unique ID for use as a tag identifier
+
+       RETURNS:        None
+******************************************************************************/
 static IMG_VOID
 MMU_UnmapPagesAndFreePTs (MMU_HEAP *psMMUHeap,
                                                  IMG_DEV_VIRTADDR sDevVAddr,
@@ -2099,39 +2684,48 @@ MMU_UnmapPagesAndFreePTs (MMU_HEAP *psMMUHeap,
 #if !defined (PDUMP)
        PVR_UNREFERENCED_PARAMETER(hUniqueTag);
 #endif
-       
+       /* setup tmp devvaddr to base of allocation */
        sTmpDevVAddr = sDevVAddr;
 
        for(i=0; i<ui32PageCount; i++)
        {
                MMU_PT_INFO **ppsPTInfoList;
 
-               
+               /* find the index/offset in PD entries  */
                ui32PDIndex = sTmpDevVAddr.uiAddr >> psMMUHeap->ui32PDShift;
 
-               
+               /* and advance to the first PT info list */
                ppsPTInfoList = &psMMUHeap->psMMUContext->apsPTInfoList[ui32PDIndex];
 
                {
-                       
+                       /* find the index/offset of the first PT in the first PT page */
                        ui32PTIndex = (sTmpDevVAddr.uiAddr & psMMUHeap->ui32PTMask) >> psMMUHeap->ui32PTShift;
 
-                       
+                       /* Is the PT page valid? */
                        if (!ppsPTInfoList[0])
                        {
-                               PVR_DPF((PVR_DBG_MESSAGE, "MMU_UnmapPagesAndFreePTs: Invalid PT for alloc at VAddr:0x%08X (VaddrIni:0x%08X AllocPage:%u) PDIdx:%u PTIdx:%u",sTmpDevVAddr.uiAddr, sDevVAddr.uiAddr,i, ui32PDIndex, ui32PTIndex ));
+                               /*
+                                       With sparse mappings we expect that the PT could be freed
+                                       before we reach the end of it as the unmapped pages don't
+                                       bump ui32ValidPTECount so it can reach zero before we reach
+                                       the end of the PT.
+                               */
+                               if (!psMMUHeap->bHasSparseMappings)
+                               {
+                                       PVR_DPF((PVR_DBG_MESSAGE, "MMU_UnmapPagesAndFreePTs: Invalid PT for alloc at VAddr:0x%08X (VaddrIni:0x%08X AllocPage:%u) PDIdx:%u PTIdx:%u",sTmpDevVAddr.uiAddr, sDevVAddr.uiAddr,i, ui32PDIndex, ui32PTIndex ));
+                               }
 
-                               
+                               /* advance the sTmpDevVAddr by one page */
                                sTmpDevVAddr.uiAddr += psMMUHeap->ui32DataPageSize;
 
-                               
+                               /* Try to unmap the remaining allocation pages */
                                continue;
                        }
 
-                       
+                       /* setup pointer to the first entry in the PT page */
                        pui32Tmp = (IMG_UINT32*)ppsPTInfoList[0]->PTPageCpuVAddr;
 
-                       
+                       /* Is PTPageCpuVAddr valid ? */
                        if (!pui32Tmp)
                        {
                                continue;
@@ -2139,37 +2733,41 @@ MMU_UnmapPagesAndFreePTs (MMU_HEAP *psMMUHeap,
 
                        CheckPT(ppsPTInfoList[0]);
 
-                       
+                       /* Decrement the valid page count only if the current page is valid*/
                        if (pui32Tmp[ui32PTIndex] & SGX_MMU_PTE_VALID)
                        {
                                ppsPTInfoList[0]->ui32ValidPTECount--;
                        }
                        else
                        {
-                               PVR_DPF((PVR_DBG_MESSAGE, "MMU_UnmapPagesAndFreePTs: Page is already invalid for alloc at VAddr:0x%08X (VAddrIni:0x%08X AllocPage:%u) PDIdx:%u PTIdx:%u",sTmpDevVAddr.uiAddr, sDevVAddr.uiAddr,i, ui32PDIndex, ui32PTIndex ));
+                               if (!psMMUHeap->bHasSparseMappings)
+                               {
+                                       PVR_DPF((PVR_DBG_MESSAGE, "MMU_UnmapPagesAndFreePTs: Page is already invalid for alloc at VAddr:0x%08X (VAddrIni:0x%08X AllocPage:%u) PDIdx:%u PTIdx:%u",sTmpDevVAddr.uiAddr, sDevVAddr.uiAddr,i, ui32PDIndex, ui32PTIndex ));
+                               }
                        }
 
-                       
+                       /* The page table count should not go below zero */
                        PVR_ASSERT((IMG_INT32)ppsPTInfoList[0]->ui32ValidPTECount >= 0);
-
+                       MakeKernelPageReadWrite(ppsPTInfoList[0]->PTPageCpuVAddr);
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-                       
+                       /* point the PT entry to the dummy data page */
                        pui32Tmp[ui32PTIndex] = (psMMUHeap->psMMUContext->psDevInfo->sDummyDataDevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                                        | SGX_MMU_PTE_VALID;
 #else
-                       
+                       /* invalidate entry */
 #if defined(FIX_HW_BRN_31620)
                        BRN31620InvalidatePageTableEntry(psMMUHeap->psMMUContext, ui32PDIndex, ui32PTIndex, &pui32Tmp[ui32PTIndex]);
 #else
                        pui32Tmp[ui32PTIndex] = 0;
 #endif
 #endif
-
+                       MakeKernelPageReadOnly(ppsPTInfoList[0]->PTPageCpuVAddr);
                        CheckPT(ppsPTInfoList[0]);
                }
 
-               
-
+               /*
+                       Free a page table if we can.
+               */
                if (ppsPTInfoList[0] && (ppsPTInfoList[0]->ui32ValidPTECount == 0)
                        )
                {
@@ -2184,7 +2782,7 @@ MMU_UnmapPagesAndFreePTs (MMU_HEAP *psMMUHeap,
 #endif
                }
 
-               
+               /* advance the sTmpDevVAddr by one page */
                sTmpDevVAddr.uiAddr += psMMUHeap->ui32DataPageSize;
        }
 
@@ -2203,10 +2801,23 @@ MMU_UnmapPagesAndFreePTs (MMU_HEAP *psMMUHeap,
                                                psMMUHeap->ui32DataPageSize * ui32PageCount,
                                                IMG_TRUE,
                                                hUniqueTag);
-#endif 
+#endif /* #if defined(PDUMP) */
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_FreePageTables
+
+       PURPOSE:    Call back from RA_Free to zero page table entries used by freed
+                               spans.
+
+       PARAMETERS: In: pvMMUHeap
+                               In: ui32Start
+                               In: ui32End
+                               In: hUniqueTag - A unique ID for use as a tag identifier
+       RETURNS:
+******************************************************************************/
 static IMG_VOID MMU_FreePageTables(IMG_PVOID pvMMUHeap,
                                    IMG_SIZE_T ui32Start,
                                    IMG_SIZE_T ui32End,
@@ -2220,6 +2831,18 @@ static IMG_VOID MMU_FreePageTables(IMG_PVOID pvMMUHeap,
        MMU_UnmapPagesAndFreePTs(pMMUHeap, Start, (IMG_UINT32)((ui32End - ui32Start) >> pMMUHeap->ui32PTShift), hUniqueTag);
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_Create
+
+       PURPOSE:    Create an mmu device virtual heap.
+
+       PARAMETERS: In: psMMUContext - MMU context
+                   In: psDevArena - device memory resource arena
+                               Out: ppsVMArena - virtual mapping arena
+       RETURNS:        MMU_HEAP
+       RETURNS:
+******************************************************************************/
 MMU_HEAP *
 MMU_Create (MMU_CONTEXT *psMMUContext,
                        DEV_ARENA_DESCRIPTOR *psDevArena,
@@ -2252,9 +2875,10 @@ MMU_Create (MMU_CONTEXT *psMMUContext,
        pMMUHeap->psMMUContext = psMMUContext;
        pMMUHeap->psDevArena = psDevArena;
 
-       
-
-
+       /*
+               generate page table and data page mask and shift values
+               based on the data page size
+       */
        switch(pMMUHeap->psDevArena->ui32DataPageSize)
        {
                case 0x1000:
@@ -2282,67 +2906,72 @@ MMU_Create (MMU_CONTEXT *psMMUContext,
                        ui32ScaleSize = 10;
                        pMMUHeap->ui32PDEPageSizeCtrl = SGX_MMU_PDE_PAGE_SIZE_4M;
                        break;
-#endif 
+#endif /* #if defined(SGX_FEATURE_VARIABLE_MMU_PAGE_SIZE) */
                default:
                        PVR_DPF((PVR_DBG_ERROR, "MMU_Create: invalid data page size"));
                        goto ErrorFreeHeap;
        }
 
-       
+       /* number of bits of address offset into the data page */
        pMMUHeap->ui32DataPageSize = psDevArena->ui32DataPageSize;
        pMMUHeap->ui32DataPageBitWidth = SGX_MMU_PAGE_SHIFT + ui32ScaleSize;
        pMMUHeap->ui32DataPageMask = pMMUHeap->ui32DataPageSize - 1;
-       
+       /* number of bits of address indexing into a pagetable */
        pMMUHeap->ui32PTShift = pMMUHeap->ui32DataPageBitWidth;
        pMMUHeap->ui32PTBitWidth = SGX_MMU_PT_SHIFT - ui32ScaleSize;
        pMMUHeap->ui32PTMask = SGX_MMU_PT_MASK & (SGX_MMU_PT_MASK<<ui32ScaleSize);
        pMMUHeap->ui32PTSize = (IMG_UINT32)(1UL<<pMMUHeap->ui32PTBitWidth) * sizeof(IMG_UINT32);
 
-       
+       /* note: PT size must be at least 4 entries, even for 4Mb data page size */
        if(pMMUHeap->ui32PTSize < 4 * sizeof(IMG_UINT32))
        {
                pMMUHeap->ui32PTSize = 4 * sizeof(IMG_UINT32);
        }
        pMMUHeap->ui32PTNumEntriesAllocated = pMMUHeap->ui32PTSize >> 2;
 
-       
+       /* find the number of actual PT entries per PD entry range. For 4MB data
+        * pages we only use the first entry although the PT has 16 byte allocation/alignment
+        * (due to 4 LSbits of the PDE are reserved for control) */
        pMMUHeap->ui32PTNumEntriesUsable = (IMG_UINT32)(1UL << pMMUHeap->ui32PTBitWidth);
 
-       
+       /* number of bits of address indexing into a page directory */
        pMMUHeap->ui32PDShift = pMMUHeap->ui32PTBitWidth + pMMUHeap->ui32PTShift;
        pMMUHeap->ui32PDBitWidth = SGX_FEATURE_ADDRESS_SPACE_SIZE - pMMUHeap->ui32PTBitWidth - pMMUHeap->ui32DataPageBitWidth;
        pMMUHeap->ui32PDMask = SGX_MMU_PD_MASK & (SGX_MMU_PD_MASK>>(32-SGX_FEATURE_ADDRESS_SPACE_SIZE));
 
-       
+       /* External system cache violates this rule */
 #if !defined (SUPPORT_EXTERNAL_SYSTEM_CACHE)
-       
-
-
-
+       /*
+               The heap must start on a PT boundary to avoid PT sharing across heaps
+               The only exception is the first heap which can start at any address
+               from 0 to the end of the first PT boundary
+       */
        if(psDevArena->BaseDevVAddr.uiAddr > (pMMUHeap->ui32DataPageMask | pMMUHeap->ui32PTMask))
        {
-               
-
-
+               /*
+                       if for some reason the first heap starts after the end of the first PT boundary
+                       but is not aligned to a PT boundary then the assert will trigger unncessarily
+               */
                PVR_ASSERT ((psDevArena->BaseDevVAddr.uiAddr
                                                & (pMMUHeap->ui32DataPageMask
                                                        | pMMUHeap->ui32PTMask)) == 0);
        }
 #endif
-       
+       /* how many PT entries do we need? */
        pMMUHeap->ui32PTETotalUsable = pMMUHeap->psDevArena->ui32Size >> pMMUHeap->ui32PTShift;
 
-       
+       /* calculate the PD Base index for the Heap (required for page mapping) */
        pMMUHeap->ui32PDBaseIndex = (pMMUHeap->psDevArena->BaseDevVAddr.uiAddr & pMMUHeap->ui32PDMask) >> pMMUHeap->ui32PDShift;
 
-       
-
-
+       /*
+               how many page tables?
+               round up to nearest entries to the nearest page table sized block
+       */
        pMMUHeap->ui32PageTableCount = (pMMUHeap->ui32PTETotalUsable + pMMUHeap->ui32PTNumEntriesUsable - 1)
                                                                                >> pMMUHeap->ui32PTBitWidth;
        PVR_ASSERT(pMMUHeap->ui32PageTableCount > 0);
 
-       
+       /* Create the arena */
        pMMUHeap->psVMArena = RA_Create(psDevArena->pszName,
                                                                        psDevArena->BaseDevVAddr.uiAddr,
                                                                        psDevArena->ui32Size,
@@ -2360,7 +2989,7 @@ MMU_Create (MMU_CONTEXT *psMMUContext,
        }
 
 #if defined(PDUMP)
-       
+       /* setup per-heap PDUMP MMU attributes */
        MMU_SetPDumpAttribs(&pMMUHeap->sMMUAttrib,
                                                psMMUContext->psDeviceNode,
                                                pMMUHeap->ui32DataPageMask,
@@ -2372,51 +3001,35 @@ MMU_Create (MMU_CONTEXT *psMMUContext,
                        psDevArena->ui32Size,
                        pMMUHeap->ui32DataPageSize,
                        psDevArena->BaseDevVAddr.uiAddr);
-#endif 
-
-#if 0 
-       
-       if(psDevArena->ui32HeapID == SGX_TILED_HEAP_ID)
-       {
-               IMG_UINT32 ui32RegVal;
-               IMG_UINT32 ui32XTileStride;
-
-               
-
-
-
-
-               ui32XTileStride = 2;
-
-               ui32RegVal = (EUR_CR_BIF_TILE0_MIN_ADDRESS_MASK
-                                               & ((psDevArena->BaseDevVAddr.uiAddr>>20)
-                                               << EUR_CR_BIF_TILE0_MIN_ADDRESS_SHIFT))
-                                       |(EUR_CR_BIF_TILE0_MAX_ADDRESS_MASK
-                                               & (((psDevArena->BaseDevVAddr.uiAddr+psDevArena->ui32Size)>>20)
-                                               << EUR_CR_BIF_TILE0_MAX_ADDRESS_SHIFT))
-                                       |(EUR_CR_BIF_TILE0_CFG_MASK
-                                               & (((ui32XTileStride<<1)|8) << EUR_CR_BIF_TILE0_CFG_SHIFT));
-               PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_BIF_TILE0, ui32RegVal);
-       }
-#endif
-
-       
+#endif /* PDUMP */
 
+       /*
+               And return the RA for VM arena management
+       */
        *ppsVMArena = pMMUHeap->psVMArena;
 
        return pMMUHeap;
 
-       
+       /* drop into here if errors */
 ErrorFreePagetables:
        _DeferredFreePageTables (pMMUHeap);
 
 ErrorFreeHeap:
        OSFreeMem (PVRSRV_OS_PAGEABLE_HEAP, sizeof(MMU_HEAP), pMMUHeap, IMG_NULL);
-       
+       /*not nulling pointer, out of scope*/
 
        return IMG_NULL;
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_Delete
+
+       PURPOSE:    Delete an MMU device virtual heap.
+
+       PARAMETERS: In:  pMMUHeap - The MMU heap to delete.
+       RETURNS:
+******************************************************************************/
 IMG_VOID
 MMU_Delete (MMU_HEAP *pMMUHeap)
 {
@@ -2434,7 +3047,7 @@ MMU_Delete (MMU_HEAP *pMMUHeap)
                                pMMUHeap->psDevArena->pszName,
                                pMMUHeap->psDevArena->BaseDevVAddr.uiAddr,
                                pMMUHeap->ui32PageTableCount);
-#endif 
+#endif /* PDUMP */
 
 #ifdef SUPPORT_SGX_MMU_BYPASS
                EnableHostAccess(pMMUHeap->psMMUContext);
@@ -2445,10 +3058,23 @@ MMU_Delete (MMU_HEAP *pMMUHeap)
 #endif
 
                OSFreeMem (PVRSRV_OS_PAGEABLE_HEAP, sizeof(MMU_HEAP), pMMUHeap, IMG_NULL);
-               
+               /*not nulling pointer, copy on stack*/
        }
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_Alloc
+       PURPOSE:    Allocate space in an mmu's virtual address space.
+       PARAMETERS:     In:  pMMUHeap - MMU to allocate on.
+                   In:  uSize - Size in bytes to allocate.
+                   Out: pActualSize - If non null receives actual size allocated.
+                   In:  uFlags - Allocation flags.
+                   In:  uDevVAddrAlignment - Required alignment.
+                   Out: DevVAddr - Receives base address of allocation.
+       RETURNS:        IMG_TRUE - Success
+                   IMG_FALSE - Failure
+******************************************************************************/
 IMG_BOOL
 MMU_Alloc (MMU_HEAP *pMMUHeap,
                   IMG_SIZE_T uSize,
@@ -2463,8 +3089,9 @@ MMU_Alloc (MMU_HEAP *pMMUHeap,
                "MMU_Alloc: uSize=0x%x, flags=0x%x, align=0x%x",
                uSize, uFlags, uDevVAddrAlignment));
 
-       
-
+       /*
+               Only allocate a VM address if the caller did not supply one
+       */
        if((uFlags & PVRSRV_MEM_USER_SUPPLIED_DEVVADDR) == 0)
        {
                IMG_UINTPTR_T uiAddr;
@@ -2476,6 +3103,8 @@ MMU_Alloc (MMU_HEAP *pMMUHeap,
                                                        0,
                                                        uDevVAddrAlignment,
                                                        0,
+                                                       IMG_NULL,
+                                                       0,
                                                        &uiAddr);
                if(!bStatus)
                {
@@ -2493,7 +3122,7 @@ MMU_Alloc (MMU_HEAP *pMMUHeap,
        EnableHostAccess(pMMUHeap->psMMUContext);
        #endif
 
-       
+       /* allocate page tables to cover allocation as required */
        bStatus = _DeferredAllocPagetables(pMMUHeap, *psDevVAddr, (IMG_UINT32)uSize);
 
        #ifdef SUPPORT_SGX_MMU_BYPASS
@@ -2509,7 +3138,7 @@ MMU_Alloc (MMU_HEAP *pMMUHeap,
                                                                pMMUHeap->psDevArena->ui32HeapID));
                if((uFlags & PVRSRV_MEM_USER_SUPPLIED_DEVVADDR) == 0)
                {
-                       
+                       /* free the VM address */
                        RA_Free (pMMUHeap->psVMArena, psDevVAddr->uiAddr, IMG_FALSE);
                }
        }
@@ -2517,6 +3146,14 @@ MMU_Alloc (MMU_HEAP *pMMUHeap,
        return bStatus;
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_Free
+       PURPOSE:    Free space in an mmu's virtual address space.
+       PARAMETERS:     In:  pMMUHeap - MMU to deallocate on.
+                   In:  DevVAddr - Base address to deallocate.
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID
 MMU_Free (MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT32 ui32Size)
 {
@@ -2546,21 +3183,52 @@ MMU_Free (MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR DevVAddr, IMG_UINT32 ui32Size)
                                                        pMMUHeap->psDevArena->ui32HeapID));
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_Enable
+
+       PURPOSE:    Enable an mmu. Establishes pages tables and takes the mmu out
+                   of bypass and waits for the mmu to acknowledge enabled.
+
+       PARAMETERS: In:  pMMUHeap - the mmu
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID
 MMU_Enable (MMU_HEAP *pMMUHeap)
 {
        PVR_UNREFERENCED_PARAMETER(pMMUHeap);
-       
+       /* SGX mmu is always enabled (stub function) */
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_Disable
+
+       PURPOSE:    Disable an mmu, takes the mmu into bypass.
+
+       PARAMETERS: In:  pMMUHeap - the mmu
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID
 MMU_Disable (MMU_HEAP *pMMUHeap)
 {
        PVR_UNREFERENCED_PARAMETER(pMMUHeap);
-       
+       /* SGX mmu is always enabled (stub function) */
 }
 
 #if defined(FIX_HW_BRN_31620)
+/*!
+******************************************************************************
+       FUNCTION:   MMU_GetCacheFlushRange
+
+       PURPOSE:    Gets device physical address of the mmu context.
+
+       PARAMETERS: In:  pMMUContext - the mmu context
+                   Out:  pui32RangeMask - Bit mask showing which PD cache
+                         lines have changed
+       RETURNS:    None
+******************************************************************************/
+
 IMG_VOID MMU_GetCacheFlushRange(MMU_CONTEXT *pMMUContext, IMG_UINT32 *pui32RangeMask)
 {
        IMG_UINT32 i;
@@ -2569,11 +3237,22 @@ IMG_VOID MMU_GetCacheFlushRange(MMU_CONTEXT *pMMUContext, IMG_UINT32 *pui32Range
        {
                pui32RangeMask[i] = pMMUContext->ui32PDChangeMask[i];
 
-               
+               /* Clear bit mask for the next set of allocations */
                pMMUContext->ui32PDChangeMask[i] = 0;
        }
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_GetPDPhysAddr
+
+       PURPOSE:    Gets device physical address of the mmu contexts PD.
+
+       PARAMETERS: In:  pMMUContext - the mmu context
+                   Out:  psDevPAddr - Address of PD
+       RETURNS:    None
+******************************************************************************/
+
 IMG_VOID MMU_GetPDPhysAddr(MMU_CONTEXT *pMMUContext, IMG_DEV_PHYADDR *psDevPAddr)
 {
        *psDevPAddr = pMMUContext->sPDDevPAddr;
@@ -2581,6 +3260,19 @@ IMG_VOID MMU_GetPDPhysAddr(MMU_CONTEXT *pMMUContext, IMG_DEV_PHYADDR *psDevPAddr
 
 #endif
 #if defined(PDUMP)
+/*!
+******************************************************************************
+       FUNCTION:   MMU_PDumpPageTables
+
+       PURPOSE:    PDump the linear mapping for a range of pages at a specified
+                   virtual address.
+
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                   In:  DevVAddr - the device virtual address.
+                   In:  uSize - size of memory range in bytes
+                   In:  hUniqueTag - A unique ID for use as a tag identifier
+       RETURNS:    None
+******************************************************************************/
 static IMG_VOID
 MMU_PDumpPageTables    (MMU_HEAP *pMMUHeap,
                                         IMG_DEV_VIRTADDR DevVAddr,
@@ -2596,22 +3288,25 @@ MMU_PDumpPageTables     (MMU_HEAP *pMMUHeap,
        IMG_UINT32 ui32PDIndex;
        IMG_UINT32 ui32PTDumpCount;
 
-       
+#if defined(FIX_HW_BRN_31620)
+       PVRSRV_SGXDEV_INFO *psDevInfo = pMMUHeap->psMMUContext->psDevInfo;
+#endif
+       /* find number of PT entries to dump */
        ui32NumPTEntries = (IMG_UINT32)((uSize + pMMUHeap->ui32DataPageMask) >> pMMUHeap->ui32PTShift);
 
-       
+       /* find the index/offset in PD entries  */
        ui32PDIndex = DevVAddr.uiAddr >> pMMUHeap->ui32PDShift;
 
-       
+       /* set the base PT info */
        ppsPTInfoList = &pMMUHeap->psMMUContext->apsPTInfoList[ui32PDIndex];
 
-       
+       /* find the index/offset of the first PT entry in the first PT page */
        ui32PTIndex = (DevVAddr.uiAddr & pMMUHeap->ui32PTMask) >> pMMUHeap->ui32PTShift;
 
-       
+       /* pdump the PT Page modification */
        PDUMPCOMMENT("Page table mods (num entries == %08X) %s", ui32NumPTEntries, bForUnmap ? "(for unmap)" : "");
 
-       
+       /* walk the PT pages, dumping as we go */
        while(ui32NumPTEntries > 0)
        {
                MMU_PT_INFO* psPTInfo = *ppsPTInfoList++;
@@ -2627,26 +3322,68 @@ MMU_PDumpPageTables     (MMU_HEAP *pMMUHeap,
 
                if (psPTInfo)
                {
+#if defined(FIX_HW_BRN_31620)
+                       IMG_UINT32 i;
+#endif
                        IMG_UINT32 ui32Flags = 0;
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
                        ui32Flags |= ( MMU_IsHeapShared(pMMUHeap) ) ? PDUMP_FLAGS_PERSISTENT : 0;
 #endif
                        pui32PTEntry = (IMG_UINT32*)psPTInfo->PTPageCpuVAddr;
-                       PDUMPMEMPTENTRIES(&pMMUHeap->sMMUAttrib, psPTInfo->hPTPageOSMemHandle, (IMG_VOID *) &pui32PTEntry[ui32PTIndex], ui32PTDumpCount * sizeof(IMG_UINT32), ui32Flags, IMG_FALSE, PDUMP_PT_UNIQUETAG, hUniqueTag);
+#if defined(FIX_HW_BRN_31620)
+                       if ((ui32PDIndex % (BRN31620_PDE_CACHE_FILL_SIZE/BRN31620_PT_ADDRESS_RANGE_SIZE)) == BRN31620_DUMMY_PDE_INDEX)
+                       {
+                               for (i=ui32PTIndex;i<(ui32PTIndex + ui32PTDumpCount);i++)
+                               {
+                                       if (pui32PTEntry[i] == ((psDevInfo->sBRN31620DummyPageDevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
+                                                                                       | SGX_MMU_PTE_DUMMY_PAGE
+                                                                                       | SGX_MMU_PTE_READONLY
+                                                                                       | SGX_MMU_PTE_VALID))
+                                       {
+                                               PDUMPMEMPTENTRIES(&pMMUHeap->sMMUAttrib, psPTInfo->hPTPageOSMemHandle, (IMG_VOID *) &pui32PTEntry[i], sizeof(IMG_UINT32), ui32Flags, IMG_FALSE, PDUMP_PT_UNIQUETAG, PDUMP_PD_UNIQUETAG);
+                                       }
+                                       else
+                                       {
+                                               PDUMPMEMPTENTRIES(&pMMUHeap->sMMUAttrib, psPTInfo->hPTPageOSMemHandle, (IMG_VOID *) &pui32PTEntry[i], sizeof(IMG_UINT32), ui32Flags, IMG_FALSE, PDUMP_PT_UNIQUETAG, hUniqueTag);
+                                       }
+                               }
+                       }
+                       else
+#endif
+                       {
+                               PDUMPMEMPTENTRIES(&pMMUHeap->sMMUAttrib, psPTInfo->hPTPageOSMemHandle, (IMG_VOID *) &pui32PTEntry[ui32PTIndex], ui32PTDumpCount * sizeof(IMG_UINT32), ui32Flags, IMG_FALSE, PDUMP_PT_UNIQUETAG, hUniqueTag);
+                       }
                }
 
-               
+               /* decrement PT entries left */
                ui32NumPTEntries -= ui32PTDumpCount;
 
-               
+               /* reset offset in page */
                ui32PTIndex = 0;
+
+#if defined(FIX_HW_BRN_31620)
+               /* For 31620 we need to know which PD index we're working on */
+               ui32PDIndex++;
+#endif
        }
 
        PDUMPCOMMENT("Finished page table mods %s", bForUnmap ? "(for unmap)" : "");
 }
-#endif 
+#endif /* #if defined(PDUMP) */
+
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_MapPage
 
+       PURPOSE:    Create a mapping for one page at a specified virtual address.
+
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                   In:  DevVAddr - the device virtual address.
+                   In:  DevPAddr - the device physical address of the page to map.
+                   In:  ui32MemFlags - BM r/w/cache flags
+       RETURNS:    None
+******************************************************************************/
 static IMG_VOID
 MMU_MapPage (MMU_HEAP *pMMUHeap,
                         IMG_DEV_VIRTADDR DevVAddr,
@@ -2658,63 +3395,66 @@ MMU_MapPage (MMU_HEAP *pMMUHeap,
        IMG_UINT32 ui32MMUFlags = 0;
        MMU_PT_INFO **ppsPTInfoList;
 
-       
+       /* check the physical alignment of the memory to map */
        PVR_ASSERT((DevPAddr.uiAddr & pMMUHeap->ui32DataPageMask) == 0);
 
-       
-
+       /*
+               unravel the read/write/cache flags
+       */
        if(((PVRSRV_MEM_READ|PVRSRV_MEM_WRITE) & ui32MemFlags) == (PVRSRV_MEM_READ|PVRSRV_MEM_WRITE))
        {
-               
+               /* read/write */
                ui32MMUFlags = 0;
        }
        else if(PVRSRV_MEM_READ & ui32MemFlags)
        {
-               
+               /* read only */
                ui32MMUFlags |= SGX_MMU_PTE_READONLY;
        }
        else if(PVRSRV_MEM_WRITE & ui32MemFlags)
        {
-               
+               /* write only */
                ui32MMUFlags |= SGX_MMU_PTE_WRITEONLY;
        }
 
-       
+       /* cache coherency */
        if(PVRSRV_MEM_CACHE_CONSISTENT & ui32MemFlags)
        {
                ui32MMUFlags |= SGX_MMU_PTE_CACHECONSISTENT;
        }
 
 #if !defined(FIX_HW_BRN_25503)
-       
+       /* EDM protection */
        if(PVRSRV_MEM_EDM_PROTECT & ui32MemFlags)
        {
                ui32MMUFlags |= SGX_MMU_PTE_EDMPROTECT;
        }
 #endif
 
-       
-
+       /*
+               we receive a device physical address for the page that is to be mapped
+               and a device virtual address representing where it should be mapped to
+       */
 
-       
+       /* find the index/offset in PD entries  */
        ui32Index = DevVAddr.uiAddr >> pMMUHeap->ui32PDShift;
 
-       
+       /* and advance to the first PT info list */
        ppsPTInfoList = &pMMUHeap->psMMUContext->apsPTInfoList[ui32Index];
 
        CheckPT(ppsPTInfoList[0]);
 
-       
+       /* find the index/offset of the first PT in the first PT page */
        ui32Index = (DevVAddr.uiAddr & pMMUHeap->ui32PTMask) >> pMMUHeap->ui32PTShift;
 
-       
+       /* setup pointer to the first entry in the PT page */
        pui32Tmp = (IMG_UINT32*)ppsPTInfoList[0]->PTPageCpuVAddr;
 
 #if !defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
        {
                IMG_UINT32 uTmp = pui32Tmp[ui32Index];
                
-               
+               /* Is the current page already valid? (should not be unless it was allocated and not deallocated) */
 #if defined(FIX_HW_BRN_31620)
                if ((uTmp & SGX_MMU_PTE_VALID) && ((DevVAddr.uiAddr & BRN31620_PDE_CACHE_FILL_MASK) != BRN31620_DUMMY_PAGE_OFFSET))
 #else
@@ -2728,6 +3468,9 @@ MMU_MapPage (MMU_HEAP *pMMUHeap,
                                                                        ui32Index ));
                        PVR_DPF((PVR_DBG_ERROR, "MMU_MapPage: Page table entry value: 0x%08X", uTmp));
                        PVR_DPF((PVR_DBG_ERROR, "MMU_MapPage: Physical page to map: 0x%08X", DevPAddr.uiAddr));
+#if PT_DUMP
+                       DumpPT(ppsPTInfoList[0]);
+#endif
                }
 #if !defined(FIX_HW_BRN_31620)
                PVR_ASSERT((uTmp & SGX_MMU_PTE_VALID) == 0);
@@ -2735,19 +3478,36 @@ MMU_MapPage (MMU_HEAP *pMMUHeap,
        }
 #endif
 
-       
+       /* One more valid entry in the page table. */
        ppsPTInfoList[0]->ui32ValidPTECount++;
 
-       
+       MakeKernelPageReadWrite(ppsPTInfoList[0]->PTPageCpuVAddr);
+       /* map in the physical page */
        pui32Tmp[ui32Index] = ((DevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                & ((~pMMUHeap->ui32DataPageMask)>>SGX_MMU_PTE_ADDR_ALIGNSHIFT))
                                                | SGX_MMU_PTE_VALID
                                                | ui32MMUFlags;
-
+       MakeKernelPageReadOnly(ppsPTInfoList[0]->PTPageCpuVAddr);
        CheckPT(ppsPTInfoList[0]);
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_MapScatter
+
+       PURPOSE:    Create a linear mapping for a range of pages at a specified
+                   virtual address.
+
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                   In:  DevVAddr - the device virtual address.
+                   In:  psSysAddr - the device physical address of the page to
+                        map.
+                   In:  uSize - size of memory range in bytes
+                In:  ui32MemFlags - page table flags.
+                   In:  hUniqueTag - A unique ID for use as a tag identifier
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID
 MMU_MapScatter (MMU_HEAP *pMMUHeap,
                                IMG_DEV_VIRTADDR DevVAddr,
@@ -2758,7 +3518,7 @@ MMU_MapScatter (MMU_HEAP *pMMUHeap,
 {
 #if defined(PDUMP)
        IMG_DEV_VIRTADDR MapBaseDevVAddr;
-#endif 
+#endif /*PDUMP*/
        IMG_UINT32 uCount, i;
        IMG_DEV_PHYADDR DevPAddr;
 
@@ -2768,7 +3528,7 @@ MMU_MapScatter (MMU_HEAP *pMMUHeap,
        MapBaseDevVAddr = DevVAddr;
 #else
        PVR_UNREFERENCED_PARAMETER(hUniqueTag);
-#endif 
+#endif /*PDUMP*/
 
        for (i=0, uCount=0; uCount<uSize; i++, uCount+=pMMUHeap->ui32DataPageSize)
        {
@@ -2777,7 +3537,7 @@ MMU_MapScatter (MMU_HEAP *pMMUHeap,
                sSysAddr = psSysAddr[i];
 
 
-               
+               /* check the physical alignment of the memory to map */
                PVR_ASSERT((sSysAddr.uiAddr & pMMUHeap->ui32DataPageMask) == 0);
 
                DevPAddr = SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sSysAddr);
@@ -2792,9 +3552,25 @@ MMU_MapScatter (MMU_HEAP *pMMUHeap,
 
 #if defined(PDUMP)
        MMU_PDumpPageTables (pMMUHeap, MapBaseDevVAddr, uSize, IMG_FALSE, hUniqueTag);
-#endif 
+#endif /* #if defined(PDUMP) */
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_MapPages
+
+       PURPOSE:    Create a linear mapping for a ranege of pages at a specified
+                   virtual address.
+
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                   In:  DevVAddr - the device virtual address.
+                   In:  SysPAddr - the system physical address of the page to
+                        map.
+                   In:  uSize - size of memory range in bytes
+                In:  ui32MemFlags - page table flags.
+                   In:  hUniqueTag - A unique ID for use as a tag identifier
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID
 MMU_MapPages (MMU_HEAP *pMMUHeap,
                          IMG_DEV_VIRTADDR DevVAddr,
@@ -2806,7 +3582,7 @@ MMU_MapPages (MMU_HEAP *pMMUHeap,
        IMG_DEV_PHYADDR DevPAddr;
 #if defined(PDUMP)
        IMG_DEV_VIRTADDR MapBaseDevVAddr;
-#endif 
+#endif /*PDUMP*/
        IMG_UINT32 uCount;
        IMG_UINT32 ui32VAdvance;
        IMG_UINT32 ui32PAdvance;
@@ -2820,7 +3596,7 @@ MMU_MapPages (MMU_HEAP *pMMUHeap,
                                                                SysPAddr.uiAddr,
                                                                uSize));
 
-       
+       /* set the virtual and physical advance */
        ui32VAdvance = pMMUHeap->ui32DataPageSize;
        ui32PAdvance = pMMUHeap->ui32DataPageSize;
 
@@ -2828,40 +3604,153 @@ MMU_MapPages (MMU_HEAP *pMMUHeap,
        MapBaseDevVAddr = DevVAddr;
 #else
        PVR_UNREFERENCED_PARAMETER(hUniqueTag);
-#endif 
+#endif /*PDUMP*/
 
        DevPAddr = SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, SysPAddr);
 
-       
+       /* check the physical alignment of the memory to map */
        PVR_ASSERT((DevPAddr.uiAddr & pMMUHeap->ui32DataPageMask) == 0);
 
-#if defined(FIX_HW_BRN_23281)
-       if(ui32MemFlags & PVRSRV_MEM_INTERLEAVED)
+       /*
+               for dummy allocations there is only one physical
+               page backing the virtual range
+       */
+       if(ui32MemFlags & PVRSRV_MEM_DUMMY)
        {
-               ui32VAdvance *= 2;
+               ui32PAdvance = 0;
        }
+
+       for (uCount=0; uCount<uSize; uCount+=ui32VAdvance)
+       {
+               MMU_MapPage (pMMUHeap, DevVAddr, DevPAddr, ui32MemFlags);
+               DevVAddr.uiAddr += ui32VAdvance;
+               DevPAddr.uiAddr += ui32PAdvance;
+       }
+
+#if defined(PDUMP)
+       MMU_PDumpPageTables (pMMUHeap, MapBaseDevVAddr, uSize, IMG_FALSE, hUniqueTag);
+#endif /* #if defined(PDUMP) */
+}
+
+
+/*!
+******************************************************************************
+       FUNCTION:   MMU_MapPagesSparse
+
+       PURPOSE:    Create a linear mapping for a ranege of pages at a specified
+                   virtual address.
+
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                   In:  DevVAddr - the device virtual address.
+                   In:  SysPAddr - the system physical address of the page to
+                        map.
+                               In:  ui32ChunkSize - Size of the chunk (must be page multiple)
+                               In:  ui32NumVirtChunks - Number of virtual chunks
+                               In:  ui32NumPhysChunks - Number of physical chunks
+                               In:  pabMapChunk - Mapping array
+                In:  ui32MemFlags - page table flags.
+                   In:  hUniqueTag - A unique ID for use as a tag identifier
+       RETURNS:    None
+******************************************************************************/
+IMG_VOID
+MMU_MapPagesSparse (MMU_HEAP *pMMUHeap,
+                                       IMG_DEV_VIRTADDR DevVAddr,
+                                       IMG_SYS_PHYADDR SysPAddr,
+                                       IMG_UINT32 ui32ChunkSize,
+                                       IMG_UINT32 ui32NumVirtChunks,
+                                       IMG_UINT32 ui32NumPhysChunks,
+                                       IMG_BOOL *pabMapChunk,
+                                       IMG_UINT32 ui32MemFlags,
+                                       IMG_HANDLE hUniqueTag)
+{
+       IMG_DEV_PHYADDR DevPAddr;
+#if defined(PDUMP)
+       IMG_DEV_VIRTADDR MapBaseDevVAddr;
+#endif /*PDUMP*/
+       IMG_UINT32 uCount;
+       IMG_UINT32 ui32VAdvance;
+       IMG_UINT32 ui32PAdvance;
+       IMG_SIZE_T uSizeVM = ui32ChunkSize * ui32NumVirtChunks;
+#if !defined(PVRSRV_NEED_PVR_DPF)
+       PVR_UNREFERENCED_PARAMETER(ui32NumPhysChunks);
 #endif
 
-       
+       PVR_ASSERT (pMMUHeap != IMG_NULL);
 
+       PVR_DPF ((PVR_DBG_MESSAGE, "MMU_MapPagesSparse: heap:%s, heap_id:%d devVAddr=%08X, SysPAddr=%08X, VM space=0x%x, PHYS space=0x%x",
+                                                               pMMUHeap->psDevArena->pszName,
+                                                               pMMUHeap->psDevArena->ui32HeapID,
+                                                               DevVAddr.uiAddr, 
+                                                               SysPAddr.uiAddr,
+                                                               uSizeVM,
+                                                               ui32ChunkSize * ui32NumPhysChunks));
 
+       /* set the virtual and physical advance */
+       ui32VAdvance = pMMUHeap->ui32DataPageSize;
+       ui32PAdvance = pMMUHeap->ui32DataPageSize;
+
+#if defined(PDUMP)
+       MapBaseDevVAddr = DevVAddr;
+#else
+       PVR_UNREFERENCED_PARAMETER(hUniqueTag);
+#endif /*PDUMP*/
+
+       DevPAddr = SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, SysPAddr);
+
+       /* check the physical alignment of the memory to map */
+       PVR_ASSERT((DevPAddr.uiAddr & pMMUHeap->ui32DataPageMask) == 0);
+
+       /*
+               for dummy allocations there is only one physical
+               page backing the virtual range
+       */
        if(ui32MemFlags & PVRSRV_MEM_DUMMY)
        {
                ui32PAdvance = 0;
        }
 
-       for (uCount=0; uCount<uSize; uCount+=ui32VAdvance)
+       for (uCount=0; uCount<uSizeVM; uCount+=ui32VAdvance)
        {
-               MMU_MapPage (pMMUHeap, DevVAddr, DevPAddr, ui32MemFlags);
+               if (pabMapChunk[uCount/ui32ChunkSize])
+               {
+                       MMU_MapPage (pMMUHeap, DevVAddr, DevPAddr, ui32MemFlags);
+                       DevPAddr.uiAddr += ui32PAdvance;
+               }
                DevVAddr.uiAddr += ui32VAdvance;
-               DevPAddr.uiAddr += ui32PAdvance;
        }
+       pMMUHeap->bHasSparseMappings = IMG_TRUE;
 
 #if defined(PDUMP)
-       MMU_PDumpPageTables (pMMUHeap, MapBaseDevVAddr, uSize, IMG_FALSE, hUniqueTag);
-#endif 
+       MMU_PDumpPageTables (pMMUHeap, MapBaseDevVAddr, uSizeVM, IMG_FALSE, hUniqueTag);
+#endif /* #if defined(PDUMP) */
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_MapShadow
+
+       PURPOSE:    Create a mapping for a range of pages from either a CPU
+                               virtual adddress, (or if NULL a hOSMemHandle) to a specified
+                               device virtual address.
+
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                In:  MapBaseDevVAddr - A page aligned device virtual address
+                                       to start mapping from.
+                In:  uByteSize - A page aligned mapping length in bytes.
+                In:  CpuVAddr - A page aligned CPU virtual address.
+                In:  hOSMemHandle - An alternative OS specific memory handle
+                                    for mapping RAM without a CPU virtual
+                                    address
+                Out: pDevVAddr - deprecated - It used to return a byte aligned
+                                 device virtual address corresponding to the
+                                 cpu virtual address (When CpuVAddr wasn't
+                                 constrained to be page aligned.) Now it just
+                                 returns MapBaseDevVAddr. Unaligned semantics
+                                 can easily be handled above this API if required.
+                In: hUniqueTag - A unique ID for use as a tag identifier
+                In: ui32MemFlags - page table flags.
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID
 MMU_MapShadow (MMU_HEAP          *pMMUHeap,
                           IMG_DEV_VIRTADDR   MapBaseDevVAddr,
@@ -2888,31 +3777,25 @@ MMU_MapShadow (MMU_HEAP          *pMMUHeap,
                        uByteSize,
                        (IMG_UINTPTR_T)CpuVAddr));
 
-       
+       /* set the virtual and physical advance */
        ui32VAdvance = pMMUHeap->ui32DataPageSize;
        ui32PAdvance = pMMUHeap->ui32DataPageSize;
 
-       
+       /* note: can't do useful check on the CPU Addr other than it being at least 4k alignment */
        PVR_ASSERT(((IMG_UINTPTR_T)CpuVAddr & (SGX_MMU_PAGE_SIZE - 1)) == 0);
        PVR_ASSERT(((IMG_UINT32)uByteSize & pMMUHeap->ui32DataPageMask) == 0);
        pDevVAddr->uiAddr = MapBaseDevVAddr.uiAddr;
 
-#if defined(FIX_HW_BRN_23281)
-       if(ui32MemFlags & PVRSRV_MEM_INTERLEAVED)
-       {
-               ui32VAdvance *= 2;
-       }
-#endif
-
-       
-
-
+       /*
+               for dummy allocations there is only one physical
+               page backing the virtual range
+       */
        if(ui32MemFlags & PVRSRV_MEM_DUMMY)
        {
                ui32PAdvance = 0;
        }
 
-       
+       /* Loop through cpu memory and map page by page */
        MapDevVAddr = MapBaseDevVAddr;
        for (i=0; i<uByteSize; i+=ui32VAdvance)
        {
@@ -2930,7 +3813,7 @@ MMU_MapShadow (MMU_HEAP          *pMMUHeap,
                }
                DevPAddr = SysCpuPAddrToDevPAddr (PVRSRV_DEVICE_TYPE_SGX, CpuPAddr);
 
-               
+               /* check the physical alignment of the memory to map */
                PVR_ASSERT((DevPAddr.uiAddr & pMMUHeap->ui32DataPageMask) == 0);
 
                PVR_DPF ((PVR_DBG_MESSAGE,
@@ -2943,17 +3826,157 @@ MMU_MapShadow (MMU_HEAP          *pMMUHeap,
 
                MMU_MapPage (pMMUHeap, MapDevVAddr, DevPAddr, ui32MemFlags);
 
-               
+               /* loop update */
                MapDevVAddr.uiAddr += ui32VAdvance;
                uOffset += ui32PAdvance;
        }
 
 #if defined(PDUMP)
        MMU_PDumpPageTables (pMMUHeap, MapBaseDevVAddr, uByteSize, IMG_FALSE, hUniqueTag);
-#endif 
+#endif /* #if defined(PDUMP) */
+}
+
+/*!
+******************************************************************************
+       FUNCTION:   MMU_MapShadowSparse
+
+       PURPOSE:    Create a mapping for a range of pages from either a CPU
+                               virtual adddress, (or if NULL a hOSMemHandle) to a specified
+                               device virtual address.
+
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                In:  MapBaseDevVAddr - A page aligned device virtual address
+                                       to start mapping from.
+                               In:  ui32ChunkSize - Size of the chunk (must be page multiple)
+                               In:  ui32NumVirtChunks - Number of virtual chunks
+                               In:  ui32NumPhysChunks - Number of physical chunks
+                               In:  pabMapChunk - Mapping array
+                In:  CpuVAddr - A page aligned CPU virtual address.
+                In:  hOSMemHandle - An alternative OS specific memory handle
+                                    for mapping RAM without a CPU virtual
+                                    address
+                Out: pDevVAddr - deprecated - It used to return a byte aligned
+                                 device virtual address corresponding to the
+                                 cpu virtual address (When CpuVAddr wasn't
+                                 constrained to be page aligned.) Now it just
+                                 returns MapBaseDevVAddr. Unaligned semantics
+                                 can easily be handled above this API if required.
+                In: hUniqueTag - A unique ID for use as a tag identifier
+                In: ui32MemFlags - page table flags.
+       RETURNS:    None
+******************************************************************************/
+IMG_VOID
+MMU_MapShadowSparse (MMU_HEAP          *pMMUHeap,
+                                        IMG_DEV_VIRTADDR   MapBaseDevVAddr,
+                                        IMG_UINT32         ui32ChunkSize,
+                                        IMG_UINT32         ui32NumVirtChunks,
+                                        IMG_UINT32         ui32NumPhysChunks,
+                                        IMG_BOOL          *pabMapChunk,
+                                        IMG_CPU_VIRTADDR   CpuVAddr,
+                                        IMG_HANDLE         hOSMemHandle,
+                                        IMG_DEV_VIRTADDR  *pDevVAddr,
+                                        IMG_UINT32         ui32MemFlags,
+                                        IMG_HANDLE         hUniqueTag)
+{
+       IMG_UINT32                      i;
+       IMG_UINT32                      uOffset = 0;
+       IMG_DEV_VIRTADDR        MapDevVAddr;
+       IMG_UINT32                      ui32VAdvance;
+       IMG_UINT32                      ui32PAdvance;
+       IMG_SIZE_T                      uiSizeVM = ui32ChunkSize * ui32NumVirtChunks;
+       IMG_UINT32                      ui32ChunkIndex = 0;
+       IMG_UINT32                      ui32ChunkOffset = 0;
+#if !defined(PVRSRV_NEED_PVR_DPF)
+       PVR_UNREFERENCED_PARAMETER(ui32NumPhysChunks);
+#endif
+#if !defined (PDUMP)
+       PVR_UNREFERENCED_PARAMETER(hUniqueTag);
+#endif
+
+       PVR_DPF ((PVR_DBG_MESSAGE,
+                       "MMU_MapShadowSparse: DevVAddr:%08X, VM space:0x%x, CPUVAddr:%08X PHYS space:0x%x",
+                       MapBaseDevVAddr.uiAddr,
+                       uiSizeVM,
+                       (IMG_UINTPTR_T)CpuVAddr,
+                       ui32ChunkSize * ui32NumPhysChunks));
+
+       /* set the virtual and physical advance */
+       ui32VAdvance = pMMUHeap->ui32DataPageSize;
+       ui32PAdvance = pMMUHeap->ui32DataPageSize;
+
+       /* note: can't do useful check on the CPU Addr other than it being at least 4k alignment */
+       PVR_ASSERT(((IMG_UINTPTR_T)CpuVAddr & (SGX_MMU_PAGE_SIZE - 1)) == 0);
+       PVR_ASSERT(((IMG_UINT32)uiSizeVM & pMMUHeap->ui32DataPageMask) == 0);
+       pDevVAddr->uiAddr = MapBaseDevVAddr.uiAddr;
+
+       /* Shouldn't come through the sparse interface */
+       PVR_ASSERT((ui32MemFlags & PVRSRV_MEM_DUMMY) == 0);
+
+       /* Loop through cpu memory and map page by page */
+       MapDevVAddr = MapBaseDevVAddr;
+       for (i=0; i<uiSizeVM; i+=ui32VAdvance)
+       {
+               IMG_CPU_PHYADDR CpuPAddr;
+               IMG_DEV_PHYADDR DevPAddr;
+
+               if (pabMapChunk[i/ui32ChunkSize])
+               /*if (pabMapChunk[ui32ChunkIndex])*/
+               {
+                       if(CpuVAddr)
+                       {
+                               CpuPAddr = OSMapLinToCPUPhys (hOSMemHandle,
+                                                                                         (IMG_VOID *)((IMG_UINTPTR_T)CpuVAddr + uOffset));
+                       }
+                       else
+                       {
+                               CpuPAddr = OSMemHandleToCpuPAddr(hOSMemHandle, uOffset);
+                       }
+                       DevPAddr = SysCpuPAddrToDevPAddr (PVRSRV_DEVICE_TYPE_SGX, CpuPAddr);
+       
+                       /* check the physical alignment of the memory to map */
+                       PVR_ASSERT((DevPAddr.uiAddr & pMMUHeap->ui32DataPageMask) == 0);
+       
+                       PVR_DPF ((PVR_DBG_MESSAGE,
+                                       "Offset=0x%x: CpuVAddr=%08X, CpuPAddr=%08X, DevVAddr=%08X, DevPAddr=%08X",
+                                       uOffset,
+                                       (IMG_UINTPTR_T)CpuVAddr + uOffset,
+                                       CpuPAddr.uiAddr,
+                                       MapDevVAddr.uiAddr,
+                                       DevPAddr.uiAddr));
+       
+                       MMU_MapPage (pMMUHeap, MapDevVAddr, DevPAddr, ui32MemFlags);
+                       uOffset += ui32PAdvance;
+               }
+
+               /* loop update */
+               MapDevVAddr.uiAddr += ui32VAdvance;
+
+               if (ui32ChunkOffset == ui32ChunkSize)
+               {
+                       ui32ChunkIndex++;
+                       ui32ChunkOffset = 0;
+               }
+       }
+
+       pMMUHeap->bHasSparseMappings = IMG_TRUE;
+#if defined(PDUMP)
+       MMU_PDumpPageTables (pMMUHeap, MapBaseDevVAddr, uiSizeVM, IMG_FALSE, hUniqueTag);
+#endif /* #if defined(PDUMP) */
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_UnmapPages
+
+       PURPOSE:    unmap pages and invalidate virtual address
 
+       PARAMETERS:     In:  psMMUHeap - the mmu.
+                   In:  sDevVAddr - the device virtual address.
+                   In:  ui32PageCount - page count
+                   In:  hUniqueTag - A unique ID for use as a tag identifier
+
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID
 MMU_UnmapPages (MMU_HEAP *psMMUHeap,
                                IMG_DEV_VIRTADDR sDevVAddr,
@@ -2971,24 +3994,24 @@ MMU_UnmapPages (MMU_HEAP *psMMUHeap,
        PVR_UNREFERENCED_PARAMETER(hUniqueTag);
 #endif
 
-       
+       /* setup tmp devvaddr to base of allocation */
        sTmpDevVAddr = sDevVAddr;
 
        for(i=0; i<ui32PageCount; i++)
        {
                MMU_PT_INFO **ppsPTInfoList;
 
-               
+               /* find the index/offset in PD entries  */
                ui32PDIndex = sTmpDevVAddr.uiAddr >> psMMUHeap->ui32PDShift;
 
-               
+               /* and advance to the first PT info list */
                ppsPTInfoList = &psMMUHeap->psMMUContext->apsPTInfoList[ui32PDIndex];
 
-               
+               /* find the index/offset of the first PT in the first PT page */
                ui32PTIndex = (sTmpDevVAddr.uiAddr & psMMUHeap->ui32PTMask) >> psMMUHeap->ui32PTShift;
 
-               
-               if (!ppsPTInfoList[0])
+               /* Is the PT page valid? */
+               if ((!ppsPTInfoList[0]) && (!psMMUHeap->bHasSparseMappings))
                {
                        PVR_DPF((PVR_DBG_ERROR, "MMU_UnmapPages: ERROR Invalid PT for alloc at VAddr:0x%08X (VaddrIni:0x%08X AllocPage:%u) PDIdx:%u PTIdx:%u",
                                                                        sTmpDevVAddr.uiAddr,
@@ -2997,19 +4020,19 @@ MMU_UnmapPages (MMU_HEAP *psMMUHeap,
                                                                        ui32PDIndex,
                                                                        ui32PTIndex));
 
-                       
+                       /* advance the sTmpDevVAddr by one page */
                        sTmpDevVAddr.uiAddr += uPageSize;
 
-                       
+                       /* Try to unmap the remaining allocation pages */
                        continue;
                }
 
                CheckPT(ppsPTInfoList[0]);
 
-               
+               /* setup pointer to the first entry in the PT page */
                pui32Tmp = (IMG_UINT32*)ppsPTInfoList[0]->PTPageCpuVAddr;
 
-               
+               /* Decrement the valid page count only if the current page is valid*/
                if (pui32Tmp[ui32PTIndex] & SGX_MMU_PTE_VALID)
                {
                        ppsPTInfoList[0]->ui32ValidPTECount--;
@@ -3025,25 +4048,27 @@ MMU_UnmapPages (MMU_HEAP *psMMUHeap,
                        PVR_DPF((PVR_DBG_ERROR, "MMU_UnmapPages: Page table entry value: 0x%08X", pui32Tmp[ui32PTIndex]));
                }
 
-               
+               /* The page table count should not go below zero */
                PVR_ASSERT((IMG_INT32)ppsPTInfoList[0]->ui32ValidPTECount >= 0);
 
+               MakeKernelPageReadWrite(ppsPTInfoList[0]->PTPageCpuVAddr);
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-               
+               /* point the PT entry to the dummy data page */
                pui32Tmp[ui32PTIndex] = (psMMUHeap->psMMUContext->psDevInfo->sDummyDataDevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                                | SGX_MMU_PTE_VALID;
 #else
-               
+               /* invalidate entry */
 #if defined(FIX_HW_BRN_31620)
                BRN31620InvalidatePageTableEntry(psMMUHeap->psMMUContext, ui32PDIndex, ui32PTIndex, &pui32Tmp[ui32PTIndex]);
 #else
                pui32Tmp[ui32PTIndex] = 0;
 #endif
 #endif
+               MakeKernelPageReadOnly(ppsPTInfoList[0]->PTPageCpuVAddr);
 
                CheckPT(ppsPTInfoList[0]);
 
-               
+               /* advance the sTmpDevVAddr by one page */
                sTmpDevVAddr.uiAddr += uPageSize;
        }
 
@@ -3051,10 +4076,21 @@ MMU_UnmapPages (MMU_HEAP *psMMUHeap,
 
 #if defined(PDUMP)
        MMU_PDumpPageTables (psMMUHeap, sDevVAddr, uPageSize*ui32PageCount, IMG_TRUE, hUniqueTag);
-#endif 
+#endif /* #if defined(PDUMP) */
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_GetPhysPageAddr
+
+       PURPOSE:    extracts physical address from MMU page tables
+
+       PARAMETERS: In:  pMMUHeap - the mmu
+       PARAMETERS: In:  sDevVPageAddr - the virtual address to extract physical
+                                       page mapping from
+       RETURNS:    None
+******************************************************************************/
 IMG_DEV_PHYADDR
 MMU_GetPhysPageAddr(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR sDevVPageAddr)
 {
@@ -3063,31 +4099,35 @@ MMU_GetPhysPageAddr(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR sDevVPageAddr)
        IMG_DEV_PHYADDR sDevPAddr;
        MMU_PT_INFO **ppsPTInfoList;
 
-       
+       /* find the index/offset in PD entries  */
        ui32Index = sDevVPageAddr.uiAddr >> pMMUHeap->ui32PDShift;
 
-       
+       /* and advance to the first PT info list */
        ppsPTInfoList = &pMMUHeap->psMMUContext->apsPTInfoList[ui32Index];
        if (!ppsPTInfoList[0])
        {
-               PVR_DPF((PVR_DBG_ERROR,"MMU_GetPhysPageAddr: Not mapped in at 0x%08x", sDevVPageAddr.uiAddr));
+               /* Heaps with sparse mappings are allowed invalid pages */
+               if (!pMMUHeap->bHasSparseMappings)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,"MMU_GetPhysPageAddr: Not mapped in at 0x%08x", sDevVPageAddr.uiAddr));
+               }
                sDevPAddr.uiAddr = 0;
                return sDevPAddr;
        }
 
-       
+       /* find the index/offset of the first PT in the first PT page */
        ui32Index = (sDevVPageAddr.uiAddr & pMMUHeap->ui32PTMask) >> pMMUHeap->ui32PTShift;
 
-       
+       /* setup pointer to the first entry in the PT page */
        pui32PageTable = (IMG_UINT32*)ppsPTInfoList[0]->PTPageCpuVAddr;
 
-       
+       /* read back physical page */
        sDevPAddr.uiAddr = pui32PageTable[ui32Index];
 
-       
+       /* Mask off non-address bits */
        sDevPAddr.uiAddr &= ~(pMMUHeap->ui32DataPageMask>>SGX_MMU_PTE_ADDR_ALIGNSHIFT);
 
-       
+       /* and align the address */
        sDevPAddr.uiAddr <<= SGX_MMU_PTE_ADDR_ALIGNSHIFT;
 
        return sDevPAddr;
@@ -3100,6 +4140,18 @@ IMG_DEV_PHYADDR MMU_GetPDDevPAddr(MMU_CONTEXT *pMMUContext)
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   SGXGetPhysPageAddr
+
+       PURPOSE:    Gets DEV and CPU physical address of sDevVAddr
+
+       PARAMETERS: In:  hDevMemHeap - device mem heap handle
+       PARAMETERS: In:  sDevVAddr - the base virtual address to unmap from
+       PARAMETERS: Out: pDevPAddr - DEV physical address
+       PARAMETERS: Out: pCpuPAddr - CPU physical address
+       RETURNS:    None
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR SGXGetPhysPageAddrKM (IMG_HANDLE hDevMemHeap,
                                                                   IMG_DEV_VIRTADDR sDevVAddr,
@@ -3109,18 +4161,30 @@ PVRSRV_ERROR SGXGetPhysPageAddrKM (IMG_HANDLE hDevMemHeap,
        MMU_HEAP *pMMUHeap;
        IMG_DEV_PHYADDR DevPAddr;
 
-       
-
+       /*
+               Get MMU Heap From hDevMemHeap
+       */
        pMMUHeap = (MMU_HEAP*)BM_GetMMUHeap(hDevMemHeap);
 
        DevPAddr = MMU_GetPhysPageAddr(pMMUHeap, sDevVAddr);
-       pCpuPAddr->uiAddr = DevPAddr.uiAddr; 
+       pCpuPAddr->uiAddr = DevPAddr.uiAddr; /* SysDevPAddrToCPUPAddr(DevPAddr) */
        pDevPAddr->uiAddr = DevPAddr.uiAddr;
 
        return (pDevPAddr->uiAddr != 0) ? PVRSRV_OK : PVRSRV_ERROR_INVALID_PARAMS;
 }
 
 
+/*!
+******************************************************************************
+    FUNCTION:   SGXGetMMUPDAddrKM
+
+    PURPOSE:    Gets PD device physical address of hDevMemContext
+
+    PARAMETERS: In:  hDevCookie - device cookie
+       PARAMETERS: In:  hDevMemContext - memory context
+       PARAMETERS: Out: psPDDevPAddr - MMU PD address
+    RETURNS:    None
+******************************************************************************/
 PVRSRV_ERROR SGXGetMMUPDAddrKM(IMG_HANDLE              hDevCookie,
                                                                IMG_HANDLE              hDevMemContext,
                                                                IMG_DEV_PHYADDR *psPDDevPAddr)
@@ -3130,12 +4194,24 @@ PVRSRV_ERROR SGXGetMMUPDAddrKM(IMG_HANDLE               hDevCookie,
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* return the address */
        *psPDDevPAddr = ((BM_CONTEXT*)hDevMemContext)->psMMUContext->sPDDevPAddr;
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_BIFResetPDAlloc
+
+       PURPOSE:    Allocate a dummy Page Directory, Page Table and Page which can
+                               be used for dynamic dummy page mapping during SGX reset.
+                               Note: since this is only used for hardware recovery, no
+                               pdumping is performed.
+
+       PARAMETERS: In:  psDevInfo - device info
+       RETURNS:    PVRSRV_OK or error
+******************************************************************************/
 PVRSRV_ERROR MMU_BIFResetPDAlloc(PVRSRV_SGXDEV_INFO *psDevInfo)
 {
        PVRSRV_ERROR eError;
@@ -3150,13 +4226,16 @@ PVRSRV_ERROR MMU_BIFResetPDAlloc(PVRSRV_SGXDEV_INFO *psDevInfo)
 
        psLocalDevMemArena = psSysData->apsLocalDevMemArena[0];
 
-       
+       /* allocate 3 pages - for the PD, PT and dummy page */
        if(psLocalDevMemArena == IMG_NULL)
        {
-               
+               /* UMA system */
                eError = OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
                                                      3 * SGX_MMU_PAGE_SIZE,
                                                      SGX_MMU_PAGE_SIZE,
+                                                         IMG_NULL,
+                                                         0,
+                                                         IMG_NULL,
                                                      (IMG_VOID **)&pui8MemBlock,
                                                      &hOSMemHandle);
                if (eError != PVRSRV_OK)
@@ -3165,7 +4244,7 @@ PVRSRV_ERROR MMU_BIFResetPDAlloc(PVRSRV_SGXDEV_INFO *psDevInfo)
                        return eError;
                }
 
-               
+               /* translate address to device physical */
                if(pui8MemBlock)
                {
                        sMemBlockCpuPAddr = OSMapLinToCPUPhys(hOSMemHandle,
@@ -3173,13 +4252,14 @@ PVRSRV_ERROR MMU_BIFResetPDAlloc(PVRSRV_SGXDEV_INFO *psDevInfo)
                }
                else
                {
-                       
+                       /* This isn't used in all cases since not all ports currently support
+                        * OSMemHandleToCpuPAddr() */
                        sMemBlockCpuPAddr = OSMemHandleToCpuPAddr(hOSMemHandle, 0);
                }
        }
        else
        {
-               
+               /* non-UMA system */
 
                if(RA_Alloc(psLocalDevMemArena,
                                        3 * SGX_MMU_PAGE_SIZE,
@@ -3188,13 +4268,15 @@ PVRSRV_ERROR MMU_BIFResetPDAlloc(PVRSRV_SGXDEV_INFO *psDevInfo)
                                        0,
                                        SGX_MMU_PAGE_SIZE,
                                        0,
+                                       IMG_NULL,
+                                       0,
                                        &(sMemBlockSysPAddr.uiAddr)) != IMG_TRUE)
                {
                        PVR_DPF((PVR_DBG_ERROR, "MMU_BIFResetPDAlloc: ERROR call to RA_Alloc failed"));
                        return PVRSRV_ERROR_OUT_OF_MEMORY;
                }
 
-               
+               /* derive the CPU virtual address */
                sMemBlockCpuPAddr = SysSysPAddrToCpuPAddr(sMemBlockSysPAddr);
                pui8MemBlock = OSMapPhysToLin(sMemBlockCpuPAddr,
                                                                          SGX_MMU_PAGE_SIZE * 3,
@@ -3211,20 +4293,29 @@ PVRSRV_ERROR MMU_BIFResetPDAlloc(PVRSRV_SGXDEV_INFO *psDevInfo)
        psDevInfo->sBIFResetPDDevPAddr = SysCpuPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sMemBlockCpuPAddr);
        psDevInfo->sBIFResetPTDevPAddr.uiAddr = psDevInfo->sBIFResetPDDevPAddr.uiAddr + SGX_MMU_PAGE_SIZE;
        psDevInfo->sBIFResetPageDevPAddr.uiAddr = psDevInfo->sBIFResetPTDevPAddr.uiAddr + SGX_MMU_PAGE_SIZE;
-       
-       
+       /* override pointer cast warnings */
+       /* PRQA S 3305,509 2 */
        psDevInfo->pui32BIFResetPD = (IMG_UINT32 *)pui8MemBlock;
        psDevInfo->pui32BIFResetPT = (IMG_UINT32 *)(pui8MemBlock + SGX_MMU_PAGE_SIZE);
 
-       
+       /* Invalidate entire PD and PT. */
        OSMemSet(psDevInfo->pui32BIFResetPD, 0, SGX_MMU_PAGE_SIZE);
        OSMemSet(psDevInfo->pui32BIFResetPT, 0, SGX_MMU_PAGE_SIZE);
-       
+       /* Fill dummy page with markers. */
        OSMemSet(pui8MemBlock + (2 * SGX_MMU_PAGE_SIZE), 0xDB, SGX_MMU_PAGE_SIZE);
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_BIFResetPDFree
+
+       PURPOSE:    Free resources allocated in MMU_BIFResetPDAlloc.
+
+       PARAMETERS: In:  psDevInfo - device info
+       RETURNS:
+******************************************************************************/
 IMG_VOID MMU_BIFResetPDFree(PVRSRV_SGXDEV_INFO *psDevInfo)
 {
        SYS_DATA *psSysData;
@@ -3235,7 +4326,7 @@ IMG_VOID MMU_BIFResetPDFree(PVRSRV_SGXDEV_INFO *psDevInfo)
 
        psLocalDevMemArena = psSysData->apsLocalDevMemArena[0];
 
-       
+       /* free the page directory */
        if(psLocalDevMemArena == IMG_NULL)
        {
                OSFreePages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
@@ -3255,274 +4346,60 @@ IMG_VOID MMU_BIFResetPDFree(PVRSRV_SGXDEV_INFO *psDevInfo)
        }
 }
 
-
-#if defined(FIX_HW_BRN_22997) && defined(FIX_HW_BRN_23030) && defined(SGX_FEATURE_HOST_PORT)
-PVRSRV_ERROR WorkaroundBRN22997Alloc(PVRSRV_DEVICE_NODE        *psDeviceNode)
+IMG_VOID MMU_CheckFaultAddr(PVRSRV_SGXDEV_INFO *psDevInfo, IMG_UINT32 ui32PDDevPAddr, IMG_UINT32 ui32FaultAddr)
 {
-       PVRSRV_ERROR eError;
-       SYS_DATA *psSysData;
-       RA_ARENA *psLocalDevMemArena;
-       IMG_HANDLE hPTPageOSMemHandle = IMG_NULL;
-       IMG_HANDLE hPDPageOSMemHandle = IMG_NULL;
-       IMG_UINT32 *pui32PD = IMG_NULL;
-       IMG_UINT32 *pui32PT = IMG_NULL;
-       IMG_CPU_PHYADDR sCpuPAddr;
-       IMG_DEV_PHYADDR sPTDevPAddr;
-       IMG_DEV_PHYADDR sPDDevPAddr;
-       PVRSRV_SGXDEV_INFO *psDevInfo;
-       IMG_UINT32 ui32PDOffset;
-       IMG_UINT32 ui32PTOffset;
-
-       psDevInfo = (PVRSRV_SGXDEV_INFO *)psDeviceNode->pvDevice;
-
-       SysAcquireData(&psSysData);
-
-       psLocalDevMemArena = psSysData->apsLocalDevMemArena[0];
+       MMU_CONTEXT *psMMUContext = psDevInfo->pvMMUContextList;
 
-       
-       if(psLocalDevMemArena == IMG_NULL)
+       while (psMMUContext && (psMMUContext->sPDDevPAddr.uiAddr != ui32PDDevPAddr))
        {
-               
-               eError = OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                  SGX_MMU_PAGE_SIZE,
-                                                  SGX_MMU_PAGE_SIZE,
-                                                  (IMG_VOID **)&pui32PT,
-                                                  &hPTPageOSMemHandle);
-               if (eError != PVRSRV_OK)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "WorkaroundBRN22997: ERROR call to OSAllocPages failed"));
-                       return eError;
-               }
-               ui32PTOffset = 0;
-
-               eError = OSAllocPages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                  SGX_MMU_PAGE_SIZE,
-                                                  SGX_MMU_PAGE_SIZE,
-                                                  (IMG_VOID **)&pui32PD,
-                                                  &hPDPageOSMemHandle);
-               if (eError != PVRSRV_OK)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "WorkaroundBRN22997: ERROR call to OSAllocPages failed"));
-                       return eError;
-               }
-               ui32PDOffset = 0;
-
-               
-               if(pui32PT)
-        {
-            sCpuPAddr = OSMapLinToCPUPhys(hPTPageOSMemHandle,
-                                                                                 pui32PT);
-        }
-        else
-        {
-            
-            sCpuPAddr = OSMemHandleToCpuPAddr(hPTPageOSMemHandle, 0);
-        }
-               sPTDevPAddr = SysCpuPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sCpuPAddr);
-
-               if(pui32PD)
-        {
-            sCpuPAddr = OSMapLinToCPUPhys(hPDPageOSMemHandle,
-                                                                                 pui32PD);
-        }
-        else
-        {
-            
-            sCpuPAddr = OSMemHandleToCpuPAddr(hPDPageOSMemHandle, 0);
-        }
-               sPDDevPAddr = SysCpuPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sCpuPAddr);
-
-       }
-       else
-       {
-               
-
-               if(RA_Alloc(psLocalDevMemArena,
-                                       SGX_MMU_PAGE_SIZE * 2,
-                                       IMG_NULL,
-                                       IMG_NULL,
-                                       0,
-                                       SGX_MMU_PAGE_SIZE,
-                                       0,
-                                       &(psDevInfo->sBRN22997SysPAddr.uiAddr))!= IMG_TRUE)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "WorkaroundBRN22997: ERROR call to RA_Alloc failed"));
-                       return PVRSRV_ERROR_OUT_OF_MEMORY;
-               }
-
-               
-               sCpuPAddr = SysSysPAddrToCpuPAddr(psDevInfo->sBRN22997SysPAddr);
-               pui32PT = OSMapPhysToLin(sCpuPAddr,
-                                                               SGX_MMU_PAGE_SIZE * 2,
-                                PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
-                                                               &hPTPageOSMemHandle);
-               if(!pui32PT)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "WorkaroundBRN22997: ERROR failed to map page tables"));
-                       return PVRSRV_ERROR_BAD_MAPPING;
-               }
-               ui32PTOffset = 0;
-
-               
-               sPTDevPAddr = SysCpuPAddrToDevPAddr(PVRSRV_DEVICE_TYPE_SGX, sCpuPAddr);
-               
-               pui32PD = pui32PT + SGX_MMU_PAGE_SIZE/sizeof(IMG_UINT32);
-               ui32PDOffset = SGX_MMU_PAGE_SIZE;
-               hPDPageOSMemHandle = hPTPageOSMemHandle;
-               sPDDevPAddr.uiAddr = sPTDevPAddr.uiAddr + SGX_MMU_PAGE_SIZE;
+               psMMUContext = psMMUContext->psNext;
        }
 
-       OSMemSet(pui32PD, 0, SGX_MMU_PAGE_SIZE);
-       OSMemSet(pui32PT, 0, SGX_MMU_PAGE_SIZE);
-
-       
-       PDUMPMALLOCPAGETABLE(&psDeviceNode->sDevId, hPDPageOSMemHandle, ui32PDOffset, pui32PD, SGX_MMU_PAGE_SIZE, 0, PDUMP_PD_UNIQUETAG);
-       PDUMPMALLOCPAGETABLE(&psDeviceNode->sDevId, hPTPageOSMemHandle, ui32PTOffset, pui32PT, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
-       PDUMPMEMPTENTRIES(&psDevInfo->sMMUAttrib, hPDPageOSMemHandle, pui32PD, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
-       PDUMPMEMPTENTRIES(&psDevInfo->sMMUAttrib, hPTPageOSMemHandle, pui32PT, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PT_UNIQUETAG, PDUMP_PD_UNIQUETAG);
-
-       psDevInfo->hBRN22997PTPageOSMemHandle = hPTPageOSMemHandle;
-       psDevInfo->hBRN22997PDPageOSMemHandle = hPDPageOSMemHandle;
-       psDevInfo->sBRN22997PTDevPAddr = sPTDevPAddr;
-       psDevInfo->sBRN22997PDDevPAddr = sPDDevPAddr;
-       psDevInfo->pui32BRN22997PD = pui32PD;
-       psDevInfo->pui32BRN22997PT = pui32PT;
-
-       return PVRSRV_OK;
-}
-
-
-IMG_VOID WorkaroundBRN22997ReadHostPort(PVRSRV_SGXDEV_INFO *psDevInfo)
-{
-       IMG_UINT32 *pui32PD = psDevInfo->pui32BRN22997PD;
-       IMG_UINT32 *pui32PT = psDevInfo->pui32BRN22997PT;
-       IMG_UINT32 ui32PDIndex;
-       IMG_UINT32 ui32PTIndex;
-       IMG_DEV_VIRTADDR sDevVAddr;
-       volatile IMG_UINT32 *pui32HostPort;
-       IMG_UINT32 ui32BIFCtrl;
-
-       
-       
-       
-       pui32HostPort = (volatile IMG_UINT32*)(((IMG_UINT8*)psDevInfo->pvHostPortBaseKM) + SYS_SGX_HOSTPORT_BRN23030_OFFSET);
-
-       
-       sDevVAddr.uiAddr = SYS_SGX_HOSTPORT_BASE_DEVVADDR + SYS_SGX_HOSTPORT_BRN23030_OFFSET;
-
-       ui32PDIndex = (sDevVAddr.uiAddr & SGX_MMU_PD_MASK) >> (SGX_MMU_PAGE_SHIFT + SGX_MMU_PT_SHIFT);
-       ui32PTIndex = (sDevVAddr.uiAddr & SGX_MMU_PT_MASK) >> SGX_MMU_PAGE_SHIFT;
-
-       
-       pui32PD[ui32PDIndex] = (psDevInfo->sBRN22997PTDevPAddr.uiAddr>>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
-                                                       | SGX_MMU_PDE_VALID;
-       
-       pui32PT[ui32PTIndex] = (psDevInfo->sBRN22997PTDevPAddr.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
-                                                       | SGX_MMU_PTE_VALID;
-
-       PDUMPMEMPTENTRIES(&psDevInfo->sMMUAttrib, psDevInfo->hBRN22997PDPageOSMemHandle, pui32PD, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
-       PDUMPMEMPTENTRIES(&psDevInfo->sMMUAttrib, psDevInfo->hBRN22997PTPageOSMemHandle, pui32PT, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PT_UNIQUETAG, PDUMP_PD_UNIQUETAG);
-
-       
-       OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_DIR_LIST_BASE0,
-                                psDevInfo->sBRN22997PDDevPAddr.uiAddr);
-       PDUMPPDREG(&psDevInfo->sMMUAttrib, EUR_CR_BIF_DIR_LIST_BASE0, psDevInfo->sBRN22997PDDevPAddr.uiAddr, PDUMP_PD_UNIQUETAG);
-
-       
-       ui32BIFCtrl = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL);
-       OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32BIFCtrl | EUR_CR_BIF_CTRL_INVALDC_MASK);
-       PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_BIF_CTRL, ui32BIFCtrl | EUR_CR_BIF_CTRL_INVALDC_MASK);
-       OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32BIFCtrl);
-       PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_BIF_CTRL, ui32BIFCtrl);
-
-       
-       if (pui32HostPort)
+       if (psMMUContext)
        {
-                
-               IMG_UINT32 ui32Tmp;
-               ui32Tmp = *pui32HostPort;
-       }
-       else
-       {
-               PVR_DPF((PVR_DBG_ERROR,"Host Port not present for BRN22997 workaround"));
-       }
-
-       
-
-
-
+               IMG_UINT32 ui32PTIndex;
+               IMG_UINT32 ui32PDIndex;
 
-       
-       PDUMPCOMMENT("RDW :SGXMEM:v4:%08X\r\n", sDevVAddr.uiAddr);
-       
-    PDUMPCOMMENT("SAB :SGXMEM:v4:%08X 4 0 hostport.bin", sDevVAddr.uiAddr);
-
-       
-       pui32PD[ui32PDIndex] = 0;
-       pui32PT[ui32PTIndex] = 0;
-
-       
-       PDUMPMEMPTENTRIES(&psDevInfo->sMMUAttrib, psDevInfo->hBRN22997PDPageOSMemHandle, pui32PD, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
-       PDUMPMEMPTENTRIES(&psDevInfo->sMMUAttrib, psDevInfo->hBRN22997PTPageOSMemHandle, pui32PT, SGX_MMU_PAGE_SIZE, 0, IMG_TRUE, PDUMP_PT_UNIQUETAG, PDUMP_PD_UNIQUETAG);
+               PVR_LOG(("Found MMU context for page fault 0x%08x", ui32FaultAddr));
+               PVR_LOG(("GPU memory context is for PID=%d (%s)", psMMUContext->ui32PID, psMMUContext->szName));
 
-       OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32BIFCtrl | EUR_CR_BIF_CTRL_INVALDC_MASK);
-       PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_BIF_CTRL, ui32BIFCtrl | EUR_CR_BIF_CTRL_INVALDC_MASK);
-       OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32BIFCtrl);
-       PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_BIF_CTRL, ui32BIFCtrl);
-}
+               ui32PTIndex = (ui32FaultAddr & SGX_MMU_PT_MASK) >> SGX_MMU_PAGE_SHIFT;
+               ui32PDIndex = (ui32FaultAddr & SGX_MMU_PD_MASK) >> (SGX_MMU_PT_SHIFT + SGX_MMU_PAGE_SHIFT);
 
-
-IMG_VOID WorkaroundBRN22997Free(PVRSRV_DEVICE_NODE *psDeviceNode)
-{
-       SYS_DATA *psSysData;
-       RA_ARENA *psLocalDevMemArena;
-       PVRSRV_SGXDEV_INFO *psDevInfo = (PVRSRV_SGXDEV_INFO*)psDeviceNode->pvDevice;
-
-
-       SysAcquireData(&psSysData);
-
-       psLocalDevMemArena = psSysData->apsLocalDevMemArena[0];
-
-       PDUMPFREEPAGETABLE(&psDeviceNode->sDevId, psDevInfo->hBRN22997PDPageOSMemHandle, psDevInfo->pui32BRN22997PD, SGX_MMU_PAGE_SIZE, 0, PDUMP_PD_UNIQUETAG);
-       PDUMPFREEPAGETABLE(&psDeviceNode->sDevId, psDevInfo->hBRN22997PTPageOSMemHandle, psDevInfo->pui32BRN22997PT, SGX_MMU_PAGE_SIZE, 0, PDUMP_PT_UNIQUETAG);
-
-       
-       if(psLocalDevMemArena == IMG_NULL)
-       {
-               if (psDevInfo->pui32BRN22997PD != IMG_NULL)
+               if (psMMUContext->apsPTInfoList[ui32PDIndex])
                {
-                       OSFreePages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                 SGX_MMU_PAGE_SIZE,
-                                                 psDevInfo->pui32BRN22997PD,
-                                                 psDevInfo->hBRN22997PDPageOSMemHandle);
-               }
+                       if (psMMUContext->apsPTInfoList[ui32PDIndex]->PTPageCpuVAddr)
+                       {
+                               IMG_UINT32 *pui32Ptr = psMMUContext->apsPTInfoList[ui32PDIndex]->PTPageCpuVAddr;
+                               IMG_UINT32 ui32PTE = pui32Ptr[ui32PTIndex];
 
-               if (psDevInfo->pui32BRN22997PT != IMG_NULL)
-               {
-                       OSFreePages(PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_KERNEL_ONLY,
-                                                 SGX_MMU_PAGE_SIZE,
-                                                 psDevInfo->pui32BRN22997PT,
-                                                 psDevInfo->hBRN22997PTPageOSMemHandle);
+                               PVR_LOG(("PDE valid: PTE = 0x%08x (PhysAddr = 0x%08x, %s)",
+                                                 ui32PTE,
+                                                 ui32PTE & SGX_MMU_PTE_ADDR_MASK,
+                                                 ui32PTE & SGX_MMU_PTE_VALID?"valid":"Invalid"));
+                       }
+                       else
+                       {
+                               PVR_LOG(("Found PT info but no CPU address"));
+                       }
                }
-       }
-       else
-       {
-               if (psDevInfo->pui32BRN22997PT != IMG_NULL)
+               else
                {
-                       OSUnMapPhysToLin(psDevInfo->pui32BRN22997PT,
-                                SGX_MMU_PAGE_SIZE * 2,
-                                PVRSRV_HAP_WRITECOMBINE|PVRSRV_HAP_KERNEL_ONLY,
-                                psDevInfo->hBRN22997PTPageOSMemHandle);
-
-
-                       RA_Free(psLocalDevMemArena, psDevInfo->sBRN22997SysPAddr.uiAddr, IMG_FALSE);
+                       PVR_LOG(("No PDE found"));
                }
        }
 }
-#endif 
-
 
 #if defined(SUPPORT_EXTERNAL_SYSTEM_CACHE)
+/*!
+******************************************************************************
+       FUNCTION:   MMU_MapExtSystemCacheRegs
+
+       PURPOSE:    maps external system cache control registers into SGX MMU
+
+       PARAMETERS: In:  psDeviceNode - device node
+       RETURNS:
+******************************************************************************/
 PVRSRV_ERROR MMU_MapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        IMG_UINT32 *pui32PT;
@@ -3554,12 +4431,13 @@ PVRSRV_ERROR MMU_MapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode)
 
        pui32PT = (IMG_UINT32 *) psDeviceNode->sDevMemoryInfo.pBMKernelContext->psMMUContext->apsPTInfoList[ui32PDIndex]->PTPageCpuVAddr;
 
-       
+       MakeKernelPageReadWrite(pui32PT);
+       /* map the PT to the registers */
        pui32PT[ui32PTIndex] = (psDevInfo->sExtSysCacheRegsDevPBase.uiAddr>>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                        | SGX_MMU_PTE_VALID;
-
+       MakeKernelPageReadOnly(pui32PT);
 #if defined(PDUMP)
-       
+       /* Add the entery to the PT */
        {
                IMG_DEV_PHYADDR sDevPAddr;
                IMG_CPU_PHYADDR sCpuPAddr;
@@ -3597,6 +4475,15 @@ PVRSRV_ERROR MMU_MapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode)
 }
 
 
+/*!
+******************************************************************************
+       FUNCTION:   MMU_UnmapExtSystemCacheRegs
+
+       PURPOSE:    unmaps external system cache control registers
+
+       PARAMETERS: In:  psDeviceNode - device node
+       RETURNS:
+******************************************************************************/
 PVRSRV_ERROR MMU_UnmapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        SYS_DATA *psSysData;
@@ -3620,11 +4507,11 @@ PVRSRV_ERROR MMU_UnmapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode)
 
        psLocalDevMemArena = psSysData->apsLocalDevMemArena[0];
 
-       
+       /* unmap the MMU page table from the PD */
        ui32PDIndex = (SGX_EXT_SYSTEM_CACHE_REGS_DEVVADDR_BASE & SGX_MMU_PD_MASK) >> (SGX_MMU_PAGE_SHIFT + SGX_MMU_PT_SHIFT);
        ui32PTIndex = (SGX_EXT_SYSTEM_CACHE_REGS_DEVVADDR_BASE & SGX_MMU_PT_MASK) >> SGX_MMU_PAGE_SHIFT;
 
-       
+       /* Only unmap it if the PT hasn't already been freed */
        if (psDeviceNode->sDevMemoryInfo.pBMKernelContext->psMMUContext->apsPTInfoList[ui32PDIndex])
        {
                if (psDeviceNode->sDevMemoryInfo.pBMKernelContext->psMMUContext->apsPTInfoList[ui32PDIndex]->PTPageCpuVAddr)
@@ -3633,7 +4520,9 @@ PVRSRV_ERROR MMU_UnmapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode)
                }
        }
 
+       MakeKernelPageReadWrite(pui32PT);
        pui32PT[ui32PTIndex] = 0;
+       MakeKernelPageReadOnly(pui32PT);
 
        PDUMPMEMPTENTRIES(&sMMUAttrib, psDeviceNode->sDevMemoryInfo.pBMKernelContext->psMMUContext->hPDOSMemHandle, &pui32PT[ui32PTIndex], sizeof(IMG_UINT32), 0, IMG_FALSE, PDUMP_PD_UNIQUETAG, PDUMP_PT_UNIQUETAG);
 
@@ -3643,6 +4532,16 @@ PVRSRV_ERROR MMU_UnmapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode)
 
 
 #if PAGE_TEST
+/*!
+******************************************************************************
+       FUNCTION:   PageTest
+
+       PURPOSE:    Tests page table memory, for use during device bring-up.
+
+       PARAMETERS: In:  void* pMem - page address (CPU mapped)
+       PARAMETERS: In:  IMG_DEV_PHYADDR sDevPAddr - page device phys address
+       RETURNS:    None, provides debug output and breaks if an error is detected.
+******************************************************************************/
 static IMG_VOID PageTest(IMG_VOID* pMem, IMG_DEV_PHYADDR sDevPAddr)
 {
        volatile IMG_UINT32 ui32WriteData;
@@ -3660,7 +4559,7 @@ static IMG_VOID PageTest(IMG_VOID* pMem, IMG_DEV_PHYADDR sDevPAddr)
 
                if (ui32WriteData != ui32ReadData)
                {
-                       
+                       // Mem fault
                        PVR_DPF ((PVR_DBG_ERROR, "Error - memory page test failed at device phys address 0x%08X", sDevPAddr.uiAddr + (n<<2) ));
                        PVR_DBG_BREAK;
                        bOK = IMG_FALSE;
@@ -3676,7 +4575,7 @@ static IMG_VOID PageTest(IMG_VOID* pMem, IMG_DEV_PHYADDR sDevPAddr)
 
                if (ui32WriteData != ui32ReadData)
                {
-                       
+                       // Mem fault
                        PVR_DPF ((PVR_DBG_ERROR, "Error - memory page test failed at device phys address 0x%08X", sDevPAddr.uiAddr + (n<<2) ));
                        PVR_DBG_BREAK;
                        bOK = IMG_FALSE;
@@ -3694,3 +4593,8 @@ static IMG_VOID PageTest(IMG_VOID* pMem, IMG_DEV_PHYADDR sDevPAddr)
 }
 #endif
 
+/******************************************************************************
+ End of file (mmu.c)
+******************************************************************************/
+
+
index 59b24c4..3c849fc 100644 (file)
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          MMU Management
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Implements basic low level control of MMU.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _MMU_H_
 #define _MMU_H_
 
 #include "sgxinfokm.h"
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_Initialise
+
+       PURPOSE:    Initialise the mmu module.
+                               
+       PARAMETERS:     None
+       RETURNS:        PVRSRV_ERROR
+******************************************************************************/
 PVRSRV_ERROR
 MMU_Initialise (PVRSRV_DEVICE_NODE *psDeviceNode, MMU_CONTEXT **ppsMMUContext, IMG_DEV_PHYADDR *psPDDevPAddr);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_Finalise
+
+       PURPOSE:    Finalise the mmu module, deallocate all resources.
+                               
+       PARAMETERS:     None.
+       RETURNS:        None.
+******************************************************************************/
 IMG_VOID
 MMU_Finalise (MMU_CONTEXT *psMMUContext);
 
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_InsertHeap
+
+       PURPOSE:    Inserts shared heap into the specified context 
+                               from the kernel context
+                               
+       PARAMETERS:     None.
+       RETURNS:        None.
+******************************************************************************/
 IMG_VOID
 MMU_InsertHeap(MMU_CONTEXT *psMMUContext, MMU_HEAP *psMMUHeap);
 
+/*
+******************************************************************************
+    FUNCTION:   MMU_Create
+
+    PURPOSE:    Create an mmu device.
+
+    PARAMETERS: In: psMMUContext -
+                In: psDevArena - 
+                               Out: ppsVMArena
+    RETURNS:   MMU_HEAP
+******************************************************************************/
 MMU_HEAP *
 MMU_Create (MMU_CONTEXT *psMMUContext,
                        DEV_ARENA_DESCRIPTOR *psDevArena,
                        RA_ARENA **ppsVMArena,
                        PDUMP_MMU_ATTRIB **ppsMMUAttrib);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_Delete
+
+       PURPOSE:    Delete an mmu device.
+                               
+       PARAMETERS:     In:  pMMUHeap - The mmu to delete.
+       RETURNS:        
+******************************************************************************/
 IMG_VOID
 MMU_Delete (MMU_HEAP *pMMUHeap);
 
+/*
+******************************************************************************
+    FUNCTION:   MMU_Alloc
+    PURPOSE:    Allocate space in an mmu's virtual address space.
+    PARAMETERS:        In:  pMMUHeap - MMU to allocate on.
+                In:  uSize - Size in bytes to allocate.
+                Out: pActualSize - If non null receives actual size allocated. 
+                In:  uFlags - Allocation flags.
+                In:  uDevVAddrAlignment - Required alignment.
+                Out: pDevVAddr - Receives base address of allocation.
+    RETURNS:   IMG_TRUE - Success
+                IMG_FALSE - Failure
+******************************************************************************/
 IMG_BOOL
 MMU_Alloc (MMU_HEAP *pMMUHeap,
            IMG_SIZE_T uSize,
@@ -56,17 +133,60 @@ MMU_Alloc (MMU_HEAP *pMMUHeap,
                   IMG_UINT32 uDevVAddrAlignment,
            IMG_DEV_VIRTADDR *pDevVAddr);
 
+/*
+******************************************************************************
+    FUNCTION:   MMU_Free
+    PURPOSE:    Frees space in an mmu's virtual address space.
+    PARAMETERS:        In: pMMUHeap - MMU to free on.
+                In: DevVAddr - Base address of allocation.
+    RETURNS:   IMG_TRUE - Success
+                IMG_FALSE - Failure
+******************************************************************************/
 IMG_VOID
 MMU_Free (MMU_HEAP *pMMUHeap,
           IMG_DEV_VIRTADDR DevVAddr,
                  IMG_UINT32 ui32Size);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_Enable
+
+       PURPOSE:    Enable an mmu. Establishes pages tables and takes the mmu out
+                   of bypass and waits for the mmu to acknowledge enabled.
+                               
+       PARAMETERS:     In:  pMMUHeap - the mmu
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID 
 MMU_Enable (MMU_HEAP *pMMUHeap);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_Disable
+
+       PURPOSE:    Disable an mmu, takes the mmu into bypass.
+                               
+       PARAMETERS:     In:  pMMUHeap - the mmu
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID 
 MMU_Disable (MMU_HEAP *pMMUHeap);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_MapPages
+
+       PURPOSE:    Create a mapping for a range of pages from a device physical
+                adddress to a specified device virtual address.
+
+       PARAMETERS:     In:  pMMUHeap - the mmu.
+                   In:  DevVAddr - the device virtual address.
+                   In:  SysPAddr - the system physical address of the page to map.
+                   In:  uSize - size of memory range in bytes
+                In:  ui32MemFlags - page table flags.
+                   In:  hUniqueTag - A unique ID for use as a tag identifier 
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID
 MMU_MapPages (MMU_HEAP *pMMUHeap,
                          IMG_DEV_VIRTADDR DevVAddr,
@@ -75,22 +195,131 @@ MMU_MapPages (MMU_HEAP *pMMUHeap,
                          IMG_UINT32 ui32MemFlags,
                          IMG_HANDLE hUniqueTag);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_MapPagesSparse
+
+       PURPOSE:    Create a mapping for a range of pages from a device physical
+                adddress to a specified device virtual address.
+
+       PARAMETERS:     In:  pMMUHeap - the mmu.
+                   In:  DevVAddr - the device virtual address.
+                   In:  SysPAddr - the system physical address of the page to map.
+                               In:  ui32ChunkSize - Size of the chunk (must be page multiple)
+                               In:  ui32NumVirtChunks - Number of virtual chunks
+                               In:  ui32NumPhysChunks - Number of physical chunks
+                               In:  pabMapChunk - Mapping array
+                In:  ui32MemFlags - page table flags.
+                   In:  hUniqueTag - A unique ID for use as a tag identifier 
+       RETURNS:        None
+******************************************************************************/
+IMG_VOID
+MMU_MapPagesSparse (MMU_HEAP *pMMUHeap,
+                                       IMG_DEV_VIRTADDR DevVAddr,
+                                       IMG_SYS_PHYADDR SysPAddr,
+                                       IMG_UINT32 ui32ChunkSize,
+                                       IMG_UINT32 ui32NumVirtChunks,
+                                       IMG_UINT32 ui32NumPhysChunks,
+                                       IMG_BOOL *pabMapChunk,
+                                       IMG_UINT32 ui32MemFlags,
+                                       IMG_HANDLE hUniqueTag);
+
+/*
+******************************************************************************
+       FUNCTION:   MMU_MapShadow
+
+       PURPOSE:    Create a mapping for a range of pages from a CPU virtual
+                adddress to a specified device virtual address.
+                               
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                In:  MapBaseDevVAddr - A page aligned device virtual address
+                                       to start mapping from.
+                In:  uByteSize - A page aligned mapping length in bytes.
+                In:  CpuVAddr - A page aligned CPU virtual address.
+                In:  hOSMemHandle - An alternative OS specific memory handle
+                                    for mapping RAM without a CPU virtual
+                                    address
+                Out: pDevVAddr - deprecated
+                In: hUniqueTag - A unique ID for use as a tag identifier
+                In: ui32MemFlags - page table flags.
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID
 MMU_MapShadow (MMU_HEAP          * pMMUHeap,
                IMG_DEV_VIRTADDR    MapBaseDevVAddr,
-               IMG_SIZE_T          uByteSize, 
+               IMG_SIZE_T          uByteSize,
                IMG_CPU_VIRTADDR    CpuVAddr,
                IMG_HANDLE          hOSMemHandle,
                IMG_DEV_VIRTADDR  * pDevVAddr,
                IMG_UINT32          ui32MemFlags,
                IMG_HANDLE          hUniqueTag);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_MapShadowSparse
+
+       PURPOSE:    Create a mapping for a range of pages from a CPU virtual
+                adddress to a specified device virtual address.
+                               
+       PARAMETERS: In:  pMMUHeap - the mmu.
+                In:  MapBaseDevVAddr - A page aligned device virtual address
+                                       to start mapping from.
+                               In:  ui32ChunkSize - Size of the chunk (must be page multiple)
+                               In:  ui32NumVirtChunks - Number of virtual chunks
+                               In:  ui32NumPhysChunks - Number of physical chunks
+                               In:  pabMapChunk - Mapping array
+                In:  CpuVAddr - A page aligned CPU virtual address.
+                In:  hOSMemHandle - An alternative OS specific memory handle
+                                    for mapping RAM without a CPU virtual
+                                    address
+                Out: pDevVAddr - deprecated
+                In: hUniqueTag - A unique ID for use as a tag identifier
+                In: ui32MemFlags - page table flags.
+       RETURNS:        None
+******************************************************************************/
+IMG_VOID
+MMU_MapShadowSparse (MMU_HEAP          * pMMUHeap,
+                                        IMG_DEV_VIRTADDR    MapBaseDevVAddr,
+                                        IMG_UINT32          ui32ChunkSize,
+                                        IMG_UINT32          ui32NumVirtChunks,
+                                        IMG_UINT32          ui32NumPhysChunks,
+                                        IMG_BOOL          * pabMapChunk,
+                                        IMG_CPU_VIRTADDR    CpuVAddr,
+                                        IMG_HANDLE          hOSMemHandle,
+                                        IMG_DEV_VIRTADDR  * pDevVAddr,
+                                        IMG_UINT32          ui32MemFlags,
+                                        IMG_HANDLE          hUniqueTag);
+
+/*
+******************************************************************************
+       FUNCTION:   MMU_UnmapPages
+
+       PURPOSE:    unmaps pages and invalidates virtual address.
+                               
+       PARAMETERS:     In:  psMMUHeap - the mmu.
+                   In:  sDevVAddr - the device virtual address.
+                   In:  ui32PageCount - page count.
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID
 MMU_UnmapPages (MMU_HEAP *psMMUHeap,
              IMG_DEV_VIRTADDR sDevVAddr,
              IMG_UINT32 ui32PageCount,
              IMG_HANDLE hUniqueTag);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_MapScatter
+
+       PURPOSE:    Create a mapping for a list of pages to a specified device 
+                               virtual address.
+                               
+       PARAMETERS:     In:  pMMUHeap - the mmu.
+                   In:  DevVAddr - the device virtual address.
+                   In:  psSysAddr - the list of physical addresses of the pages to
+                        map.
+       RETURNS:        None
+******************************************************************************/
 IMG_VOID
 MMU_MapScatter (MMU_HEAP *pMMUHeap,
                                IMG_DEV_VIRTADDR DevVAddr,
@@ -100,55 +329,173 @@ MMU_MapScatter (MMU_HEAP *pMMUHeap,
                                IMG_HANDLE hUniqueTag);
 
 
+/*
+******************************************************************************
+    FUNCTION:   MMU_GetPhysPageAddr
+
+    PURPOSE:    extracts physical address from MMU page tables
+
+    PARAMETERS: In:  pMMUHeap - the mmu
+       PARAMETERS: In:  sDevVPageAddr - the virtual address to extract physical 
+                                       page mapping from
+    RETURNS:    IMG_DEV_PHYADDR
+******************************************************************************/
 IMG_DEV_PHYADDR
 MMU_GetPhysPageAddr(MMU_HEAP *pMMUHeap, IMG_DEV_VIRTADDR sDevVPageAddr);
 
 
+/*
+******************************************************************************
+    FUNCTION:   MMU_GetPDDevPAddr
+
+    PURPOSE:    returns PD given the MMU context (SGX to MMU API)
+
+    PARAMETERS: In:  pMMUContext - the mmu
+    RETURNS:    IMG_DEV_PHYADDR
+******************************************************************************/
 IMG_DEV_PHYADDR
 MMU_GetPDDevPAddr(MMU_CONTEXT *pMMUContext);
 
 
 #ifdef SUPPORT_SGX_MMU_BYPASS
+/*
+******************************************************************************
+    FUNCTION:   EnableHostAccess
+
+    PURPOSE:    Enables Host accesses to device memory, by passing the device 
+                       MMU address translation
+
+    PARAMETERS: In: psMMUContext
+    RETURNS:    None
+******************************************************************************/
 IMG_VOID
 EnableHostAccess (MMU_CONTEXT *psMMUContext);
 
 
+/*
+******************************************************************************
+    FUNCTION:   DisableHostAccess
+
+    PURPOSE:    Disables Host accesses to device memory, by passing the device 
+                       MMU address translation
+
+    PARAMETERS: In: psMMUContext
+    RETURNS:    None
+******************************************************************************/
 IMG_VOID
 DisableHostAccess (MMU_CONTEXT *psMMUContext);
 #endif
 
+/*
+******************************************************************************
+    FUNCTION:   MMU_InvalidateDirectoryCache
+
+    PURPOSE:    Invalidates the page directory cache
+
+    PARAMETERS: In: psDevInfo
+    RETURNS:    None
+******************************************************************************/
 IMG_VOID MMU_InvalidateDirectoryCache(PVRSRV_SGXDEV_INFO *psDevInfo);
 
-PVRSRV_ERROR MMU_BIFResetPDAlloc(PVRSRV_SGXDEV_INFO *psDevInfo);
+/*
+******************************************************************************
+       FUNCTION:   MMU_BIFResetPDAlloc
 
-IMG_VOID MMU_BIFResetPDFree(PVRSRV_SGXDEV_INFO *psDevInfo);
+       PURPOSE:    Allocate a dummy Page Directory which causes all virtual
+                               addresses to page fault.
 
-#if defined(FIX_HW_BRN_22997) && defined(FIX_HW_BRN_23030) && defined(SGX_FEATURE_HOST_PORT)
-PVRSRV_ERROR WorkaroundBRN22997Alloc(PVRSRV_DEVICE_NODE        *psDeviceNode);
+       PARAMETERS: In:  psDevInfo - device info
+       RETURNS:    PVRSRV_OK or error
+******************************************************************************/
+PVRSRV_ERROR MMU_BIFResetPDAlloc(PVRSRV_SGXDEV_INFO *psDevInfo);
 
-IMG_VOID WorkaroundBRN22997ReadHostPort(PVRSRV_SGXDEV_INFO *psDevInfo);
+/*
+******************************************************************************
+       FUNCTION:   MMU_BIFResetPDFree
 
-IMG_VOID WorkaroundBRN22997Free(PVRSRV_DEVICE_NODE *psDeviceNode);
-#endif 
+       PURPOSE:    Free resources allocated in MMU_BIFResetPDAlloc.
+
+       PARAMETERS: In:  psDevInfo - device info
+       RETURNS:
+******************************************************************************/
+IMG_VOID MMU_BIFResetPDFree(PVRSRV_SGXDEV_INFO *psDevInfo);
 
 #if defined(SUPPORT_EXTERNAL_SYSTEM_CACHE)
+/*
+******************************************************************************
+       FUNCTION:   MMU_MapExtSystemCacheRegs
+
+       PURPOSE:    maps external system cache control registers into SGX MMU
+
+       PARAMETERS: In:  psDeviceNode - device node
+       RETURNS:
+******************************************************************************/
 PVRSRV_ERROR MMU_MapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode);
 
-PVRSRV_ERROR MMU_UnmapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode);
-#endif 
+/*
+******************************************************************************
+       FUNCTION:   MMU_UnmapExtSystemCacheRegs
 
+       PURPOSE:    unmaps external system cache control registers
+
+       PARAMETERS: In:  psDeviceNode - device node
+       RETURNS:
+******************************************************************************/
+PVRSRV_ERROR MMU_UnmapExtSystemCacheRegs(PVRSRV_DEVICE_NODE *psDeviceNode);
+#endif /* #if defined(SUPPORT_EXTERNAL_SYSTEM_CACHE) */
+
+/*
+******************************************************************************
+       FUNCTION:   MMU_IsHeapShared
+       
+       PURPOSE:    Is this heap shared?
+       PARAMETERS: In: pMMU_Heap
+       RETURNS:    true if heap is shared
+******************************************************************************/
 IMG_BOOL MMU_IsHeapShared(MMU_HEAP* pMMU_Heap);
 
 #if defined(FIX_HW_BRN_31620)
+/*
+******************************************************************************
+       FUNCTION:   MMU_GetCacheFlushRange
+
+       PURPOSE:    Gets device physical address of the mmu context.
+
+       PARAMETERS: In:  pMMUContext - the mmu context
+                   Out:  pui32RangeMask - Bit mask showing which PD cache
+                         lines have changed
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID MMU_GetCacheFlushRange(MMU_CONTEXT *pMMUContext, IMG_UINT32 *pui32RangeMask);
 
+/*
+******************************************************************************
+       FUNCTION:   MMU_GetPDPhysAddr
+
+       PURPOSE:    Gets device physical address of the mmu contexts PD.
+
+       PARAMETERS: In:  pMMUContext - the mmu context
+                   Out:  psDevPAddr - Address of PD
+       RETURNS:    None
+******************************************************************************/
 IMG_VOID MMU_GetPDPhysAddr(MMU_CONTEXT *pMMUContext, IMG_DEV_PHYADDR *psDevPAddr);
 
 #endif
 
 
+IMG_VOID MMU_CheckFaultAddr(PVRSRV_SGXDEV_INFO *psDevInfo, IMG_UINT32 ui32PDDevPAddr, IMG_UINT32 ui32RegVal);
+
 #if defined(PDUMP)
+/*
+******************************************************************************
+       FUNCTION:   MMU_GetPDumpContextID
+
+       PURPOSE:    translates device mem context to unique pdump identifier
+
+       PARAMETERS: In:  hDevMemContext - device memory per-process context
+       RETURNS:        context identifier used internally in pdump
+******************************************************************************/
 IMG_UINT32 MMU_GetPDumpContextID(IMG_HANDLE hDevMemContext);
-#endif 
+#endif /* #ifdef PDUMP */
 
-#endif 
+#endif /* #ifndef _MMU_H_ */
index ab6523a..4ed18bb 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Parameter Buffer management functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <stddef.h>
 
@@ -35,8 +50,8 @@
 #include "pdump_km.h"
 #include "sgxutils.h"
 
-#ifndef __linux__
-#pragma message("TODO: Review use of OS_PAGEABLE vs OS_NON_PAGEABLE")
+#if !defined(__linux__) && !defined(__QNXNTO__)
+#pragma message("FIXME: Review use of OS_PAGEABLE vs OS_NON_PAGEABLE")
 #endif
 
 #include "lists.h"
@@ -50,6 +65,8 @@ static PVRSRV_PER_PROCESS_DATA *psPerProcCreateSharedPB = IMG_NULL;
 static PVRSRV_ERROR SGXCleanupSharedPBDescCallback(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bDummy);
 static PVRSRV_ERROR SGXCleanupSharedPBDescCreateLockCallback(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bDummy);
 
+/* override level pointer indirection */
+/* PRQA S 5102 12 */
 IMG_EXPORT PVRSRV_ERROR
 SGXFindSharedPBDescKM(PVRSRV_PER_PROCESS_DATA  *psPerProc,
                                          IMG_HANDLE                            hDevCookie,
@@ -108,7 +125,7 @@ SGXFindSharedPBDescKM(PVRSRV_PER_PROCESS_DATA       *psPerProc,
                                          sizeof(PVRSRV_KERNEL_MEM_INFO *) * psStubPBDesc->ui32SubKernelMemInfosCount,
                                          ppsSharedPBDescSubKernelMemInfos,
                                          0);
-                       
+                       /*not nulling pointer, out of scope*/
 
                        PVR_DPF((PVR_DBG_ERROR, "SGXFindSharedPBDescKM: ResManRegisterRes failed"));
 
@@ -173,15 +190,12 @@ ExitNotFound:
 static PVRSRV_ERROR
 SGXCleanupSharedPBDescKM(PVRSRV_STUB_PBDESC *psStubPBDescIn)
 {
-       
+       /*PVRSRV_STUB_PBDESC **ppsStubPBDesc;*/
        IMG_UINT32 i;
        PVRSRV_DEVICE_NODE *psDeviceNode;
 
        psDeviceNode = (PVRSRV_DEVICE_NODE*)psStubPBDescIn->hDevCookie;
 
-       
-
-       
        psStubPBDescIn->ui32RefCount--;
        if (psStubPBDescIn->ui32RefCount == 0)
        {
@@ -189,7 +203,6 @@ SGXCleanupSharedPBDescKM(PVRSRV_STUB_PBDESC *psStubPBDescIn)
                List_PVRSRV_STUB_PBDESC_Remove(psStubPBDescIn);
                for(i=0 ; i<psStubPBDescIn->ui32SubKernelMemInfosCount; i++)
                {
-                       
                        PVRSRVFreeDeviceMemKM(psStubPBDescIn->hDevCookie,
                                                                  psStubPBDescIn->ppsSubKernelMemInfos[i]);
                }
@@ -212,16 +225,16 @@ SGXCleanupSharedPBDescKM(PVRSRV_STUB_PBDESC *psStubPBDescIn)
                                  sizeof(PVRSRV_STUB_PBDESC),
                                  psStubPBDescIn,
                                  0);
-               
+               /*not nulling pointer, copy on stack*/
 
-               
+               /* signal the microkernel to clear its sTAHWPBDesc and s3DHWPBDesc values in sTA3DCtl */
                SGXCleanupRequest(psDeviceNode,
                                                  &sHWPBDescDevVAddr,
                                                  PVRSRV_CLEANUPCMD_PB,
                                                  CLEANUP_WITH_POLL);
        }
        return PVRSRV_OK;
-       
+       /*return PVRSRV_ERROR_INVALID_PARAMS;*/
 }
 
 static PVRSRV_ERROR SGXCleanupSharedPBDescCallback(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bDummy)
@@ -281,7 +294,10 @@ SGXAddSharedPBDescKM(PVRSRV_PER_PROCESS_DATA       *psPerProc,
        PVRSRV_SGXDEV_INFO *psSGXDevInfo;
        PRESMAN_ITEM psResItem;
 
-       
+       /*
+        * The caller must have previously called SGXFindSharedPBDesc with
+        * bLockOnFailure set, and not managed to find a suitable shared PB.
+        */
        if (psPerProcCreateSharedPB != psPerProc)
        {
                goto NoAdd;
@@ -309,7 +325,11 @@ SGXAddSharedPBDescKM(PVRSRV_PER_PROCESS_DATA       *psPerProc,
 
                }
 
-               
+               /*
+                * We make the caller think the add was successful,
+                * but return the existing shared PB desc rather than
+                * a new one.
+                */
                psResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                          RESMAN_TYPE_SHARED_PB_DESC,
                                                                          psStubPBDesc,
@@ -324,7 +344,10 @@ SGXAddSharedPBDescKM(PVRSRV_PER_PROCESS_DATA       *psPerProc,
                        goto NoAddKeepPB;
                }
 
-               
+               /*
+                * The caller will unreference the PB desc after
+                * a successful add, so up the reference count.
+                */
                psStubPBDesc->ui32RefCount++;
 
                *phSharedPBDesc = (IMG_HANDLE)psResItem;
@@ -423,7 +446,8 @@ SGXAddSharedPBDescKM(PVRSRV_PER_PROCESS_DATA        *psPerProc,
        }
        psStubPBDesc->hDevCookie = hDevCookie;
 
-       
+       /* Finally everything was prepared successfully so link the new
+        * PB in to place. */
        List_PVRSRV_STUB_PBDESC_Insert(&(psSGXDevInfo->psStubPBDescListKM),
                                                                        psStubPBDesc);
 
@@ -446,7 +470,7 @@ NoAdd:
                                  sizeof(PVRSRV_STUB_PBDESC),
                                  psStubPBDesc,
                                  0);
-               
+               /*not nulling pointer, out of scope*/
        }
 
 NoAddKeepPB:
@@ -464,3 +488,6 @@ NoAddKeepPB:
        return eRet;
 }
 
+/******************************************************************************
+ End of file (pb.c)
+******************************************************************************/
index 8fb3002..f281c4e 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX Bridge Functionality
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Header for the SGX Bridge code
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined(__SGX_BRIDGE_KM_H__)
 #define __SGX_BRIDGE_KM_H__
@@ -114,6 +130,47 @@ PVRSRV_ERROR DevInitSGXPart2KM(PVRSRV_PER_PROCESS_DATA *psPerProc,
                                                           SGX_BRIDGE_INIT_INFO *psInitInfo);
 #endif
 
+/*!
+ * *****************************************************************************
+ * @brief Looks for a parameter buffer description that corresponds to
+ *        a buffer of size ui32TotalPBSize, optionally taking the lock
+ *        needed for SharedPBCreation on failure.
+ *
+ *        Note if a PB Desc is found then its internal reference counter
+ *        is automatically incremented. It is your responsability to call
+ *        SGXUnrefSharedPBDesc to decrement this reference and free associated
+ *        resources when you are done.
+ *
+ *       If bLockOnFailure is set, and a suitable shared PB isn't found,
+ *       an internal flag is set, allowing this process to create a
+ *       shared PB.  Any other process calling this function with
+ *       bLockOnFailure set, will receive the return code
+ *       PVRSRV_ERROR_PROCESSING_BLOCKED, indicating that it needs
+ *       to retry the function call.  The internal flag is cleared
+ *       when this process creates a shared PB.
+ *
+ *       Note: You are responsible for freeing the list returned in
+ *       pppsSharedPBDescSubKernelMemInfos
+ *       via OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+ *                                     sizeof(PVRSRV_KERNEL_MEM_INFO *)
+ *                                       * ui32SharedPBDescSubKernelMemInfosCount,
+ *                                     ppsSharedPBDescSubKernelMemInfos,
+ *                                     NULL);
+ *
+ * @param[in] psPerProc
+ * @param[in] hDevCookie
+ * @param[in] bLockOnError
+ * @param[in] ui32TotalPBSize
+ * @param[in] phSharedPBDesc
+ * @param[out] ppsSharedPBDescKernelMemInfo
+ * @param[out] ppsHWPBDescKernelMemInfo
+ * @param[out] pppsSharedPBDescSubKernelMemInfos  A list of integral sub meminfos.
+ * @param[out] ui32SharedPBDescSubKernelMemInfosCount
+ *
+ * @return PVRSRV_ERROR
+ ********************************************************************************/
+/* disable QAC pointer level check for over 2 */
+/* PRQA S 5102++ */
 IMG_IMPORT PVRSRV_ERROR
 SGXFindSharedPBDescKM(PVRSRV_PER_PROCESS_DATA  *psPerProc,
                                          IMG_HANDLE                            hDevCookie,
@@ -127,9 +184,58 @@ SGXFindSharedPBDescKM(PVRSRV_PER_PROCESS_DATA      *psPerProc,
                                          PVRSRV_KERNEL_MEM_INFO        ***pppsSharedPBDescSubKernelMemInfos,
                                          IMG_UINT32                            *ui32SharedPBDescSubKernelMemInfosCount);
 
+/*!
+ * *****************************************************************************
+ * @brief Decrements the reference counter and frees all userspace resources
+ *        associated with a SharedPBDesc.
+ *
+ * @param hSharedPBDesc
+ *
+ * @return PVRSRV_ERROR
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR
 SGXUnrefSharedPBDescKM(IMG_HANDLE hSharedPBDesc);
 
+/*!
+ * *****************************************************************************
+ * @brief Links a new SharedPBDesc into a kernel managed list that can
+ *        then be queried by other clients.
+ *
+ *        As a side affect this function also dissociates the SharedPBDesc
+ *        from the calling process so that the memory won't be freed if the
+ *        process dies/exits. (The kernel assumes responsability over the
+ *        memory at the same time)
+ *
+ *        As well as the psSharedPBDescKernelMemInfo you must also pass
+ *        a complete list of other meminfos that are integral to the
+ *        shared PB description. (Although the kernel doesn't have direct
+ *        access to the shared PB desc it still needs to be able to
+ *        clean up all the associated resources when it is no longer
+ *        in use.)
+ *
+ *        If the dissociation fails then all the memory associated with
+ *       the psSharedPBDescKernelMemInfo and all entries in psKernelMemInfos
+ *       will be freed by kernel services! Because of this, you are
+ *       responsible for freeing the corresponding client meminfos _before_
+ *       calling SGXAddSharedPBDescKM.
+ *
+ *       This function will return an error unless a succesful call to
+ *       SGXFindSharedPBDesc, with bLockOnFailure set, has been made.
+ *
+ * @param psPerProc
+ * @param hDevCookie
+ * @param psSharedPBDescKernelMemInfo
+ * @param psHWPBDescKernelMemInfo
+ * @param psBlockKernelMemInfo
+ * @param ui32TotalPBSize  The size of the associated parameter buffer
+ * @param ppsSharedPBDescSubKernelMemInfos  A list of other meminfos integral to
+ *                                                                                 the shared PB description.
+ * @param ui32SharedPBDescSubKernelMemInfosCount  The number of entires in
+ *                                                                                               psKernelMemInfos
+ * @param sHWPBDescDevVAddr The device virtual address of the HWPBDesc
+ *
+ * @return PVRSRV_ERROR
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR
 SGXAddSharedPBDescKM(PVRSRV_PER_PROCESS_DATA   *psPerProc,
                                         IMG_HANDLE                             hDevCookie,
@@ -144,6 +250,16 @@ SGXAddSharedPBDescKM(PVRSRV_PER_PROCESS_DATA       *psPerProc,
                                         IMG_DEV_VIRTADDR                       sHWPBDescDevVAddr);
 
 
+/*!
+ * *****************************************************************************
+ * @brief Gets device information that is not intended to be passed
+                 on beyond the srvclient libs.
+ *
+ * @param[in] hDevCookie
+ * @param[out] psSGXInternalDevInfo
+ *
+ * @return
+ ********************************************************************************/
 IMG_IMPORT PVRSRV_ERROR
 SGXGetInternalDevInfoKM(IMG_HANDLE hDevCookie,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -156,5 +272,8 @@ SGXGetInternalDevInfoKM(IMG_HANDLE hDevCookie,
 }
 #endif
 
-#endif 
+#endif /* __SGX_BRIDGE_KM_H__ */
 
+/******************************************************************************
+ End of file (sgx_bridge_km.h)
+******************************************************************************/
index 5e38cd5..b9ebab9 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          device configuration
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __SGXCONFIG_H__
 #define __SGXCONFIG_H__
 #define SGX_KERNEL_DATA_HEAP_OFFSET            0x00000000
 #endif
 
+#if !defined(ION_HEAP_SIZE) && defined(SUPPORT_ION)
+       /* Default the Ion heap to 16MB */
+       #define ION_HEAP_SIZE                                           0x01000000
+#else
+       #define ION_HEAP_SIZE                                           0
+#endif
+
+
 #if SGX_FEATURE_ADDRESS_SPACE_SIZE == 32
 #if defined(FIX_HW_BRN_31620)
        #if defined(SGX_FEATURE_2D_HARDWARE)
        #define SGX_GENERAL_HEAP_BASE                            0x08000000
        #define SGX_GENERAL_HEAP_SIZE                           (0xB8000000-0x00001000)
 
-       
+       /*
+        * For hybrid PB we have to split virtual PB range between the shared
+        * PB and percontext PB due to the fact we only have one heap config
+        * per device.
+        * If hybrid PB is enabled we split the space acording to HYBRID_SHARED_PB_SIZE.
+        * i.e. HYBRID_SHARED_PB_SIZE defines the size of the shared PB and the
+        * remainder is the size of the percontext PB.
+        * If hybrid PB is not enabled then we still create both heaps (helps keep
+        * the code clean) and define the size of the unused one to 0
+        */
+
        #define SGX_3DPARAMETERS_HEAP_SIZE                      0x10000000
 
-       
+       /* By default we split the PB 50/50 */
 #if !defined(HYBRID_SHARED_PB_SIZE)
        #define HYBRID_SHARED_PB_SIZE                           (SGX_3DPARAMETERS_HEAP_SIZE >> 1)
 #endif
 #endif
 
        #define SGX_SHARED_3DPARAMETERS_HEAP_BASE                0xC0000000
-       
+       /* Size is defiend above */
 
        #define SGX_PERCONTEXT_3DPARAMETERS_HEAP_BASE            (SGX_SHARED_3DPARAMETERS_HEAP_BASE + SGX_SHARED_3DPARAMETERS_SIZE)
-       
+       /* Size is defiend above */
 
        #define SGX_TADATA_HEAP_BASE                             0xD0000000
        #define SGX_TADATA_HEAP_SIZE                            (0x0D000000-0x00001000)
        #define SGX_KERNEL_DATA_HEAP_BASE                       (0xF0000000+SGX_KERNEL_DATA_HEAP_OFFSET)
        #define SGX_KERNEL_DATA_HEAP_SIZE                       (0x03000000-(0x00001000+SGX_KERNEL_DATA_HEAP_OFFSET))
 
-       
+       /* Actual Pixel and Vertex shared heaps sizes may be reduced by
+        * override - see SGX_USE_CODE_SEGMENT_RANGE_BITS.*/
        #define SGX_PIXELSHADER_HEAP_BASE                        0xF4000000
        #define SGX_PIXELSHADER_HEAP_SIZE                       (0x05000000-0x00001000)
        
        #define SGX_VERTEXSHADER_HEAP_BASE                       0xFC000000
        #define SGX_VERTEXSHADER_HEAP_SIZE                      (0x02000000-0x00001000)
-#else 
+#else /* FIX_HW_BRN_31620 */
        #if defined(SGX_FEATURE_2D_HARDWARE)
        #define SGX_2D_HEAP_BASE                                         0x00100000
        #define SGX_2D_HEAP_SIZE                                        (0x08000000-0x00100000-0x00001000)
-       #else
-               #if defined(FIX_HW_BRN_26915)
-               #define SGX_CGBUFFER_HEAP_BASE                                   0x00100000
-               #define SGX_CGBUFFER_HEAP_SIZE                                  (0x08000000-0x00100000-0x00001000)
-               #endif
        #endif
 
        #if defined(SUPPORT_SGX_GENERAL_MAPPING_HEAP)
        #define SGX_GENERAL_MAPPING_HEAP_SIZE           (0x08000000-0x00001000)
        #endif
 
-       #define SGX_GENERAL_HEAP_BASE                            0x10000000
-       #define SGX_GENERAL_HEAP_SIZE                           (0xC2000000-0x00001000)
+       #if !defined(SUPPORT_MEMORY_TILING)
+               #if defined (SUPPORT_ION)
+                       #define SGX_GENERAL_HEAP_BASE                            0x10000000
+                       #define SGX_GENERAL_HEAP_SIZE                           (0xC2000000-ION_HEAP_SIZE-0x00001000)
+
+                       #define SGX_ION_HEAP_BASE                                       (SGX_GENERAL_HEAP_BASE+SGX_GENERAL_HEAP_SIZE+0x00001000)
+                       #define SGX_ION_HEAP_SIZE                                       (ION_HEAP_SIZE-0x00001000)
+               #else
+                       #define SGX_GENERAL_HEAP_BASE                            0x10000000
+                       #define SGX_GENERAL_HEAP_SIZE                           (0xC2000000-0x00001000)
+               #endif
+       #else
+               #include <sgx_msvdx_defs.h>
+               /* Create heaps with memory tiling enabled.
+                * SGX HW limit is 10 heaps.
+                */
+               /* Tiled heap space is taken from general heap */
+               #define SGX_GENERAL_HEAP_BASE                            0x10000000
+               #define SGX_GENERAL_HEAP_SIZE                           (0xB5000000-0x00001000)
+
+               #define SGX_VPB_TILED_HEAP_STRIDE                       TILING_TILE_STRIDE_2K
+               #define SGX_VPB_TILED_HEAP_BASE          0xC5000000
+               #define SGX_VPB_TILED_HEAP_SIZE (0x0D000000-0x00001000)
+
+               /* Check tiled heap base alignment */
+               #if((SGX_VPB_TILED_HEAP_BASE & SGX_BIF_TILING_ADDR_INV_MASK) != 0)
+               #error "sgxconfig.h: SGX_VPB_TILED_HEAP has insufficient alignment"
+               #endif
+
+       #endif /* SUPPORT_MEMORY_TILING */
+
+       /*
+        * For hybrid PB we have to split virtual PB range between the shared
+        * PB and percontext PB due to the fact we only have one heap config
+        * per device.
+        * If hybrid PB is enabled we split the space acording to HYBRID_SHARED_PB_SIZE.
+        * i.e. HYBRID_SHARED_PB_SIZE defines the size of the shared PB and the
+        * remainder is the size of the percontext PB.
+        * If hybrid PB is not enabled then we still create both heaps (helps keep
+        * the code clean) and define the size of the unused one to 0
+        */
 
-       
        #define SGX_3DPARAMETERS_HEAP_SIZE                      0x10000000
 
-       
+       /* By default we split the PB 50/50 */
 #if !defined(HYBRID_SHARED_PB_SIZE)
        #define HYBRID_SHARED_PB_SIZE                           (SGX_3DPARAMETERS_HEAP_SIZE >> 1)
 #endif
 #endif
 
        #define SGX_SHARED_3DPARAMETERS_HEAP_BASE                0xD2000000
-       
+       /* Size is defiend above */
 
        #define SGX_PERCONTEXT_3DPARAMETERS_HEAP_BASE            (SGX_SHARED_3DPARAMETERS_HEAP_BASE + SGX_SHARED_3DPARAMETERS_SIZE)
-       
+       /* Size is defiend above */
 
        #define SGX_TADATA_HEAP_BASE                             0xE2000000
        #define SGX_TADATA_HEAP_SIZE                            (0x0D000000-0x00001000)
        #define SGX_KERNEL_DATA_HEAP_BASE                       (0xF4000000+SGX_KERNEL_DATA_HEAP_OFFSET)
        #define SGX_KERNEL_DATA_HEAP_SIZE                       (0x05000000-(0x00001000+SGX_KERNEL_DATA_HEAP_OFFSET))
 
-       
+       /* Actual Pixel and Vertex shared heaps sizes may be reduced by
+        * override - see SGX_USE_CODE_SEGMENT_RANGE_BITS.*/
        #define SGX_PIXELSHADER_HEAP_BASE                        0xF9000000
        #define SGX_PIXELSHADER_HEAP_SIZE                       (0x05000000-0x00001000)
        
        #define SGX_VERTEXSHADER_HEAP_BASE                       0xFE000000
        #define SGX_VERTEXSHADER_HEAP_SIZE                      (0x02000000-0x00001000)
-#endif 
-       
+#endif /* FIX_HW_BRN_31620 */
+       /* signal we've identified the core by the build */
        #define SGX_CORE_IDENTIFIED
-#endif 
+#endif /* SGX_FEATURE_ADDRESS_SPACE_SIZE == 32 */
 
 #if SGX_FEATURE_ADDRESS_SPACE_SIZE == 28
 
        #define SGX_GENERAL_MAPPING_HEAP_SIZE           (0x01800000-0x00001000-0x00001000)
 
        #define SGX_GENERAL_HEAP_BASE                            0x01800000
-       #define SGX_GENERAL_HEAP_SIZE                           (0x07000000-0x00001000)
+       #define SGX_GENERAL_HEAP_SIZE                           (0x07000000-ION_HEAP_SIZE-0x00001000)
 
 #else
        #define SGX_GENERAL_HEAP_BASE                            0x00001000
-       #define SGX_GENERAL_HEAP_SIZE                           (0x08800000-0x00001000-0x00001000)
+#if defined(SUPPORT_LARGE_GENERAL_HEAP)
+       #define SGX_GENERAL_HEAP_SIZE                           (0x0B800000-ION_HEAP_SIZE-0x00001000-0x00001000)
+#else
+       #define SGX_GENERAL_HEAP_SIZE                           (0x08800000-ION_HEAP_SIZE-0x00001000-0x00001000)
 #endif
-       
+#endif
+
+#if defined(SUPPORT_ION)
+       #define SGX_ION_HEAP_BASE                                       (SGX_GENERAL_HEAP_BASE+SGX_GENERAL_HEAP_SIZE+0x00001000)
+       #define SGX_ION_HEAP_SIZE                                       (ION_HEAP_SIZE-0x00001000)
+#endif
+       /*
+        * For hybrid PB we have to split virtual PB range between the shared
+        * PB and percontext PB due to the fact we only have one heap config
+        * per device.
+        * If hybrid PB is enabled we split the space acording to HYBRID_SHARED_PB_SIZE.
+        * i.e. HYBRID_SHARED_PB_SIZE defines the size of the shared PB and the
+        * remainder is the size of the percontext PB.
+        * If hybrid PB is not enabled then we still create both heaps (helps keep
+        * the code clean) and define the size of the unused one to 0
+        */
+#if defined(SUPPORT_LARGE_GENERAL_HEAP)
+       #define SGX_3DPARAMETERS_HEAP_SIZE                      0x01000000
+#else
        #define SGX_3DPARAMETERS_HEAP_SIZE                      0x04000000
+#endif
 
-       
+       /* By default we split the PB 50/50 */
 #if !defined(HYBRID_SHARED_PB_SIZE)
        #define HYBRID_SHARED_PB_SIZE                           (SGX_3DPARAMETERS_HEAP_SIZE >> 1)
 #endif
 #endif
 #endif
 
+#if defined(SUPPORT_LARGE_GENERAL_HEAP)
+       #define SGX_SHARED_3DPARAMETERS_HEAP_BASE                0x0B800000
+#else
        #define SGX_SHARED_3DPARAMETERS_HEAP_BASE                0x08800000
-       
+#endif
+
+       /* Size is defined above */
 
        #define SGX_PERCONTEXT_3DPARAMETERS_HEAP_BASE            (SGX_SHARED_3DPARAMETERS_HEAP_BASE + SGX_SHARED_3DPARAMETERS_SIZE)
-       
+       /* Size is defined above */
 
        #define SGX_TADATA_HEAP_BASE                             0x0C800000
        #define SGX_TADATA_HEAP_SIZE                            (0x01000000-0x00001000)
        #define SGX_VERTEXSHADER_HEAP_BASE                       0x0FC00000
        #define SGX_VERTEXSHADER_HEAP_SIZE                      (0x00200000-0x00001000)
 
-       
+       /* signal we've identified the core by the build */
        #define SGX_CORE_IDENTIFIED
 
-#endif 
+#endif /* SGX_FEATURE_ADDRESS_SPACE_SIZE == 28 */
 
 #if !defined(SGX_CORE_IDENTIFIED)
        #error "sgxconfig.h: ERROR: unspecified SGX Core version"
 #endif
 
+/*********************************************************************************
+ *
+ * SGX_PDSPIXEL_CODEDATA_HEAP_BASE + 64MB range must include PDSVERTEX_CODEDATA and KERNEL_CODE heaps
+ *
+ ********************************************************************************/
 #if !defined (SGX_FEATURE_EDM_VERTEX_PDSADDR_FULL_RANGE)
        #if ((SGX_KERNEL_CODE_HEAP_BASE + SGX_KERNEL_CODE_HEAP_SIZE - SGX_PDSPIXEL_CODEDATA_HEAP_BASE) >  0x4000000)
                #error "sgxconfig.h: ERROR: SGX_KERNEL_CODE_HEAP_BASE out of range of SGX_PDSPIXEL_CODEDATA_HEAP_BASE"
        #endif
 #endif 
 
+/*********************************************************************************
+ *
+ * The General Mapping heap must be within the 2D requestor range of the 2D heap base
+ *
+ ********************************************************************************/
 #if defined(SGX_FEATURE_2D_HARDWARE) && defined(SUPPORT_SGX_GENERAL_MAPPING_HEAP)
        #if ((SGX_GENERAL_MAPPING_HEAP_BASE + SGX_GENERAL_MAPPING_HEAP_SIZE - SGX_2D_HEAP_BASE) >= EUR_CR_BIF_TWOD_REQ_BASE_ADDR_MASK)
                #error "sgxconfig.h: ERROR: SGX_GENERAL_MAPPING_HEAP inaccessable by 2D requestor"
        #endif
 #endif
 
+/*********************************************************************************
+ *
+ * The kernel code heap base must be aligned to a USSE code page
+ *
+ ********************************************************************************/
 #if defined (EURASIA_USE_CODE_PAGE_SIZE)
        #if ((SGX_KERNEL_CODE_HEAP_BASE & (EURASIA_USE_CODE_PAGE_SIZE - 1)) != 0)
                #error "sgxconfig.h: ERROR: Kernel code heap base misalignment"
        #endif
 #endif
 
+/*********************************************************************************
+ *
+ * Heap overlap check
+ *
+ ********************************************************************************/
 #if defined(SGX_FEATURE_2D_HARDWARE)
        #if defined(SUPPORT_SGX_GENERAL_MAPPING_HEAP)
                #if ((SGX_2D_HEAP_BASE + SGX_2D_HEAP_SIZE) >= SGX_GENERAL_MAPPING_HEAP_BASE)
                        #error "sgxconfig.h: ERROR: SGX_2D_HEAP overlaps SGX_GENERAL_HEAP_BASE"
                #endif
        #endif
-#else
-    #if defined(FIX_HW_BRN_26915)
-               #if defined(SUPPORT_SGX_GENERAL_MAPPING_HEAP)
-                       #if ((SGX_CGBUFFER_HEAP_BASE + SGX_CGBUFFER_HEAP_SIZE) >= SGX_GENERAL_MAPPING_HEAP_BASE)
-                               #error "sgxconfig.h: ERROR: SGX_CGBUFFER_HEAP overlaps SGX_GENERAL_MAPPING_HEAP"
-                       #endif
-               #else
-                       #if ((SGX_CGBUFFER_HEAP_BASE + SGX_CGBUFFER_HEAP_SIZE) >= SGX_GENERAL_HEAP_BASE)
-                               #error "sgxconfig.h: ERROR: SGX_CGBUFFER_HEAP overlaps SGX_GENERAL_HEAP_BASE"
-                       #endif
-               #endif
-       #endif
 #endif
 
 #if defined(SUPPORT_SGX_GENERAL_MAPPING_HEAP)
        #endif
 #endif
 
-#if ((SGX_GENERAL_HEAP_BASE + SGX_GENERAL_HEAP_SIZE) >= SGX_SHARED_3DPARAMETERS_HEAP_BASE)
-       #error "sgxconfig.h: ERROR: SGX_GENERAL_HEAP overlaps SGX_3DPARAMETERS_HEAP"
+#if defined(SUPPORT_MEMORY_TILING)
+       #if ((SGX_GENERAL_HEAP_BASE + SGX_GENERAL_HEAP_SIZE) >= SGX_VPB_TILED_HEAP_BASE)
+               #error "sgxconfig.h: ERROR: SGX_GENERAL_HEAP overlaps SGX_VPB_TILED_HEAP"
+       #endif
+       #if ((SGX_VPB_TILED_HEAP_BASE + SGX_VPB_TILED_HEAP_SIZE) >= SGX_SHARED_3DPARAMETERS_HEAP_BASE)
+               #error "sgxconfig.h: ERROR: SGX_VPB_TILED_HEAP overlaps SGX_3DPARAMETERS_HEAP"
+       #endif
+#else
+       #if defined(SUPPORT_ION)
+               #if ((SGX_ION_HEAP_BASE + SGX_ION_HEAP_SIZE) >= SGX_SHARED_3DPARAMETERS_HEAP_BASE)
+                       #error "sgxconfig.h: ERROR: SGX_ION_HEAP overlaps SGX_3DPARAMETERS_HEAP"
+               #endif
+       #endif
+       #if ((SGX_GENERAL_HEAP_BASE + SGX_GENERAL_HEAP_SIZE) >= SGX_SHARED_3DPARAMETERS_HEAP_BASE)
+               #error "sgxconfig.h: ERROR: SGX_GENERAL_HEAP overlaps SGX_3DPARAMETERS_HEAP"
+       #endif
 #endif
 
 #if (((SGX_PERCONTEXT_3DPARAMETERS_HEAP_BASE + SGX_PERCONTEXT_3DPARAMETERS_HEAP_SIZE) >= SGX_TADATA_HEAP_BASE) && (SGX_PERCONTEXT_3DPARAMETERS_HEAP_SIZE > 0))
        #error "sgxconfig.h: ERROR: SGX_VERTEXSHADER_HEAP_BASE size cause wraparound"
 #endif
 
-#endif 
+#endif /* __SGXCONFIG_H__ */
 
+/*****************************************************************************
+ End of file (sgxconfig.h)
+*****************************************************************************/
index 0ebe153..125da09 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          SGX kernel services structues/functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Structures and inline functions for KM services component
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __SGXINFOKM_H__
 #define __SGXINFOKM_H__
 
 extern "C" {
 #endif
 
+/****************************************************************************/
+/* kernel only defines:                                                                                                        */
+/****************************************************************************/
+/* SGXDeviceMap Flag defines */
 #define                SGX_HOSTPORT_PRESENT                    0x00000001UL
 
 
+/*
+       SGX PDUMP register bank name (prefix)
+*/
 #define SGX_PDUMPREG_NAME              "SGXREG"
 
+/****************************************************************************/
+/* kernel only structures:                                                                                                     */
+/****************************************************************************/
+
+/*Forward declaration*/
 typedef struct _PVRSRV_STUB_PBDESC_ PVRSRV_STUB_PBDESC;
 
 
@@ -58,103 +85,106 @@ typedef struct _PVRSRV_SGXDEV_INFO_
        IMG_UINT32                              ui32CoreConfig;
        IMG_UINT32                              ui32CoreFlags;
 
-       
+       /* Kernel mode linear address of device registers */
        IMG_PVOID                               pvRegsBaseKM;
 
 #if defined(SGX_FEATURE_HOST_PORT)
-       
+       /* Kernel mode linear address of host port */
        IMG_PVOID                               pvHostPortBaseKM;
-       
+       /* HP size */
        IMG_UINT32                              ui32HPSize;
-       
+       /* HP syspaddr */
        IMG_SYS_PHYADDR                 sHPSysPAddr;
 #endif
 
-       
+       /* FIXME: The alloc for this should go through OSAllocMem in future */
        IMG_HANDLE                              hRegMapping;
 
-       
+       /* System physical address of device registers*/
        IMG_SYS_PHYADDR                 sRegsPhysBase;
-       
+       /*  Register region size in bytes */
        IMG_UINT32                              ui32RegSize;
 
 #if defined(SUPPORT_EXTERNAL_SYSTEM_CACHE)
-       
+       /* external system cache register region size in bytes */
        IMG_UINT32                              ui32ExtSysCacheRegsSize;
-       
+       /* external system cache register device relative physical address */
        IMG_DEV_PHYADDR                 sExtSysCacheRegsDevPBase;
-       
+       /* ptr to page table  */
        IMG_UINT32                              *pui32ExtSystemCacheRegsPT;
-       
+       /* handle to page table alloc/mapping */
        IMG_HANDLE                              hExtSystemCacheRegsPTPageOSMemHandle;
-       
+       /* sys phys addr of PT */
        IMG_SYS_PHYADDR                 sExtSystemCacheRegsPTSysPAddr;
 #endif
 
-       
+       /*  SGX clock speed */
        IMG_UINT32                              ui32CoreClockSpeed;
        IMG_UINT32                              ui32uKernelTimerClock;
+       IMG_BOOL                                bSGXIdle;
 
        PVRSRV_STUB_PBDESC              *psStubPBDescListKM;
 
 
-       
+       /* kernel memory context info */
        IMG_DEV_PHYADDR                 sKernelPDDevPAddr;
 
+       IMG_UINT32                              ui32HeapCount;                  /*!< heap count */
        IMG_VOID                                *pvDeviceMemoryHeap;
-       PPVRSRV_KERNEL_MEM_INFO psKernelCCBMemInfo;                     
-       PVRSRV_SGX_KERNEL_CCB   *psKernelCCB;                   
-       PPVRSRV_SGX_CCB_INFO    psKernelCCBInfo;                
-       PPVRSRV_KERNEL_MEM_INFO psKernelCCBCtlMemInfo;  
-       PVRSRV_SGX_CCB_CTL              *psKernelCCBCtl;                
-       PPVRSRV_KERNEL_MEM_INFO psKernelCCBEventKickerMemInfo; 
-       IMG_UINT32                              *pui32KernelCCBEventKicker; 
+       PPVRSRV_KERNEL_MEM_INFO psKernelCCBMemInfo;                     /*!< meminfo for CCB in device accessible memory */
+       PVRSRV_SGX_KERNEL_CCB   *psKernelCCB;                   /*!< kernel mode linear address of CCB in device accessible memory */
+       PPVRSRV_SGX_CCB_INFO    psKernelCCBInfo;                /*!< CCB information structure */
+       PPVRSRV_KERNEL_MEM_INFO psKernelCCBCtlMemInfo;  /*!< meminfo for CCB control in device accessible memory */
+       PVRSRV_SGX_CCB_CTL              *psKernelCCBCtl;                /*!< kernel mode linear address of CCB control in device accessible memory */
+       PPVRSRV_KERNEL_MEM_INFO psKernelCCBEventKickerMemInfo; /*!< meminfo for kernel CCB event kicker */
+       IMG_UINT32                              *pui32KernelCCBEventKicker; /*!< kernel mode linear address of kernel CCB event kicker */
 #if defined(PDUMP)
-       IMG_UINT32                              ui32KernelCCBEventKickerDumpVal; 
-#endif 
-       PVRSRV_KERNEL_MEM_INFO  *psKernelSGXMiscMemInfo;        
-       IMG_UINT32                              aui32HostKickAddr[SGXMKIF_CMD_MAX];             
+       IMG_UINT32                              ui32KernelCCBEventKickerDumpVal; /*!< pdump copy of the kernel CCB event kicker */
+#endif /* PDUMP */
+       PVRSRV_KERNEL_MEM_INFO  *psKernelSGXMiscMemInfo;        /*!< kernel mode linear address of SGX misc info buffer */
+       IMG_UINT32                              aui32HostKickAddr[SGXMKIF_CMD_MAX];             /*!< ukernel host kick offests */
 #if defined(SGX_SUPPORT_HWPROFILING)
        PPVRSRV_KERNEL_MEM_INFO psKernelHWProfilingMemInfo;
 #endif
-       PPVRSRV_KERNEL_MEM_INFO         psKernelHWPerfCBMemInfo;                
-       PPVRSRV_KERNEL_MEM_INFO         psKernelTASigBufferMemInfo;             
-       PPVRSRV_KERNEL_MEM_INFO         psKernel3DSigBufferMemInfo;             
+       PPVRSRV_KERNEL_MEM_INFO         psKernelHWPerfCBMemInfo;                /*!< Meminfo for hardware performace circular buffer */
+       PPVRSRV_KERNEL_MEM_INFO         psKernelTASigBufferMemInfo;             /*!< Meminfo for TA signature buffer */
+       PPVRSRV_KERNEL_MEM_INFO         psKernel3DSigBufferMemInfo;             /*!< Meminfo for 3D signature buffer */
 #if defined(FIX_HW_BRN_29702)
-       PPVRSRV_KERNEL_MEM_INFO psKernelCFIMemInfo;     
+       PPVRSRV_KERNEL_MEM_INFO psKernelCFIMemInfo;     /*!< Meminfo for cfi */
 #endif
 #if defined(FIX_HW_BRN_29823)
-       PPVRSRV_KERNEL_MEM_INFO psKernelDummyTermStreamMemInfo; 
+       PPVRSRV_KERNEL_MEM_INFO psKernelDummyTermStreamMemInfo; /*!< Meminfo for dummy terminate stream */
 #endif
-#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31425)
-       PPVRSRV_KERNEL_MEM_INFO psKernelVDMSnapShotBufferMemInfo; 
-       PPVRSRV_KERNEL_MEM_INFO psKernelVDMCtrlStreamBufferMemInfo; 
+#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31559)
+       PPVRSRV_KERNEL_MEM_INFO psKernelVDMSnapShotBufferMemInfo; /*!< Meminfo for dummy snapshot buffer */
+       PPVRSRV_KERNEL_MEM_INFO psKernelVDMCtrlStreamBufferMemInfo; /*!< Meminfo for dummy control stream */
 #endif
 #if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && \
        defined(FIX_HW_BRN_33657) && defined(SUPPORT_SECURE_33657_FIX)
-       PPVRSRV_KERNEL_MEM_INFO psKernelVDMStateUpdateBufferMemInfo; 
+       PPVRSRV_KERNEL_MEM_INFO psKernelVDMStateUpdateBufferMemInfo; /*!< Meminfo for state update buffer */
 #endif
 #if defined(PVRSRV_USSE_EDM_STATUS_DEBUG)
-       PPVRSRV_KERNEL_MEM_INFO psKernelEDMStatusBufferMemInfo; 
+       PPVRSRV_KERNEL_MEM_INFO psKernelEDMStatusBufferMemInfo; /*!< Meminfo for EDM status buffer */
 #endif
-       
+       /* Client reference count */
        IMG_UINT32                              ui32ClientRefCount;
 
-       
+       /* cache control word for micro kernel cache flush/invalidates */
        IMG_UINT32                              ui32CacheControl;
 
-       
+       /* client-side build options */
        IMG_UINT32                              ui32ClientBuildOptions;
 
-       
+       /* client-side microkernel structure sizes */
        SGX_MISCINFO_STRUCT_SIZES       sSGXStructSizes;
 
-       
-
-
+       /*
+               if we don't preallocate the pagetables we must 
+               insert newly allocated page tables dynamically 
+       */
        IMG_VOID                                *pvMMUContextList;
 
-       
+       /* Copy of registry ForcePTOff entry */
        IMG_BOOL                                bForcePTOff;
 
        IMG_UINT32                              ui32EDMTaskReg0;
@@ -169,10 +199,10 @@ typedef struct _PVRSRV_SGXDEV_INFO_
        IMG_UINT32                              ui32MasterClkGateStatusMask;
        IMG_UINT32                              ui32MasterClkGateStatus2Reg;
        IMG_UINT32                              ui32MasterClkGateStatus2Mask;
-#endif 
+#endif /* SGX_FEATURE_MP */
        SGX_INIT_SCRIPTS                sScripts;
 
-       
+       /* Members associated with dummy PD needed for BIF reset */
        IMG_HANDLE                              hBIFResetPDOSMemHandle;
        IMG_DEV_PHYADDR                 sBIFResetPDDevPAddr;
        IMG_DEV_PHYADDR                 sBIFResetPTDevPAddr;
@@ -180,32 +210,22 @@ typedef struct _PVRSRV_SGXDEV_INFO_
        IMG_UINT32                              *pui32BIFResetPD;
        IMG_UINT32                              *pui32BIFResetPT;
 
-#if defined(FIX_HW_BRN_22997) && defined(FIX_HW_BRN_23030) && defined(SGX_FEATURE_HOST_PORT)
-       
-       IMG_HANDLE                              hBRN22997PTPageOSMemHandle;
-       IMG_HANDLE                              hBRN22997PDPageOSMemHandle;
-       IMG_DEV_PHYADDR                 sBRN22997PTDevPAddr;
-       IMG_DEV_PHYADDR                 sBRN22997PDDevPAddr;
-       IMG_UINT32                              *pui32BRN22997PT;
-       IMG_UINT32                              *pui32BRN22997PD;
-       IMG_SYS_PHYADDR                 sBRN22997SysPAddr;
-#endif 
 
 #if defined(SUPPORT_HW_RECOVERY)
-       
+       /* Timeout callback handle */
        IMG_HANDLE                              hTimer;
-       
+       /* HW recovery Time stamp */
        IMG_UINT32                              ui32TimeStamp;
 #endif
 
-       
+       /* Number of SGX resets */
        IMG_UINT32                              ui32NumResets;
 
-       
+       /* host control */
        PVRSRV_KERNEL_MEM_INFO                  *psKernelSGXHostCtlMemInfo;
        SGXMKIF_HOST_CTL                                *psSGXHostCtl;
 
-       
+       /* TA/3D control */
        PVRSRV_KERNEL_MEM_INFO                  *psKernelSGXTA3DCtlMemInfo;
 
 #if defined(FIX_HW_BRN_31272) || defined(FIX_HW_BRN_31780) || defined(FIX_HW_BRN_33920)
@@ -214,7 +234,7 @@ typedef struct _PVRSRV_SGXDEV_INFO_
 
        IMG_UINT32                              ui32Flags;
 
-       
+       /* memory tiling range usage */
        IMG_UINT32                              ui32MemTilingUsage;
 
        #if defined(PDUMP)
@@ -222,7 +242,7 @@ typedef struct _PVRSRV_SGXDEV_INFO_
        #endif
 
 #if defined(SUPPORT_SGX_MMU_DUMMY_PAGE)
-       
+       /* SGX MMU dummy page details */
        IMG_VOID                                *pvDummyPTPageCpuVAddr;
        IMG_DEV_PHYADDR                 sDummyPTDevPAddr;
        IMG_HANDLE                              hDummyPTPageOSMemHandle;
@@ -236,12 +256,12 @@ typedef struct _PVRSRV_SGXDEV_INFO_
        IMG_UINT32                              asSGXDevData[SGX_MAX_DEV_DATA];
 
 #if defined(FIX_HW_BRN_31620)
-       
+       /* Dummy page refs */
        IMG_VOID                        *pvBRN31620DummyPageCpuVAddr;
        IMG_HANDLE                      hBRN31620DummyPageOSMemHandle;
        IMG_DEV_PHYADDR                 sBRN31620DummyPageDevPAddr;
 
-       
+       /* Dummy PT refs */
        IMG_VOID                        *pvBRN31620DummyPTCpuVAddr;
        IMG_HANDLE                      hBRN31620DummyPTOSMemHandle;
        IMG_DEV_PHYADDR                 sBRN31620DummyPTDevPAddr;
@@ -261,11 +281,13 @@ typedef struct _SGX_TIMING_INFORMATION_
        IMG_UINT32                      ui32uKernelFreq;
 } SGX_TIMING_INFORMATION;
 
+/* FIXME Rename this structure to sg more generalised as it's been extended*/
+/* SGX device map */
 typedef struct _SGX_DEVICE_MAP_
 {
        IMG_UINT32                              ui32Flags;
 
-       
+       /* Registers */
        IMG_SYS_PHYADDR                 sRegsSysPBase;
        IMG_CPU_PHYADDR                 sRegsCpuPBase;
        IMG_CPU_VIRTADDR                pvRegsCpuVBase;
@@ -277,7 +299,7 @@ typedef struct _SGX_DEVICE_MAP_
        IMG_UINT32                              ui32HPSize;
 #endif
 
-       
+       /* Local Device Memory Region: (if present) */
        IMG_SYS_PHYADDR                 sLocalMemSysPBase;
        IMG_DEV_PHYADDR                 sLocalMemDevPBase;
        IMG_CPU_PHYADDR                 sLocalMemCpuPBase;
@@ -288,15 +310,15 @@ typedef struct _SGX_DEVICE_MAP_
        IMG_DEV_PHYADDR                 sExtSysCacheRegsDevPBase;
 #endif
 
-       
+       /* device interrupt IRQ */
        IMG_UINT32                              ui32IRQ;
 
 #if !defined(SGX_DYNAMIC_TIMING_INFO)
-       
+       /* timing information*/
        SGX_TIMING_INFORMATION  sTimingInfo;
 #endif
 #if defined(PDUMP)
-       
+       /* pdump memory region name */
        IMG_CHAR                                *pszPDumpDevName;
 #endif
 } SGX_DEVICE_MAP;
@@ -318,15 +340,19 @@ struct _PVRSRV_STUB_PBDESC_
        PVRSRV_STUB_PBDESC      **ppsThis;
 };
 
+/*!
+ ******************************************************************************
+ * CCB control structure for SGX
+ *****************************************************************************/
 typedef struct _PVRSRV_SGX_CCB_INFO_
 {
-       PVRSRV_KERNEL_MEM_INFO  *psCCBMemInfo;                  
-       PVRSRV_KERNEL_MEM_INFO  *psCCBCtlMemInfo;               
-       SGXMKIF_COMMAND         *psCommands;                    
-       IMG_UINT32                              *pui32WriteOffset;              
-       volatile IMG_UINT32             *pui32ReadOffset;               
+       PVRSRV_KERNEL_MEM_INFO  *psCCBMemInfo;                  /*!< meminfo for CCB in device accessible memory */
+       PVRSRV_KERNEL_MEM_INFO  *psCCBCtlMemInfo;               /*!< meminfo for CCB control in device accessible memory */
+       SGXMKIF_COMMAND         *psCommands;                    /*!< linear address of the array of commands */
+       IMG_UINT32                              *pui32WriteOffset;              /*!< linear address of the write offset into array of commands */
+       volatile IMG_UINT32             *pui32ReadOffset;               /*!< linear address of the read offset into array of commands */
 #if defined(PDUMP)
-       IMG_UINT32                              ui32CCBDumpWOff;                
+       IMG_UINT32                              ui32CCBDumpWOff;                /*!< for pdumping */
 #endif
 } PVRSRV_SGX_CCB_INFO;
 
@@ -375,7 +401,11 @@ typedef struct _SGX_BRIDGE_INIT_INFO_KM_
        IMG_UINT32 ui32ClkGateStatusReg;
        IMG_UINT32 ui32ClkGateStatusMask;
 #if defined(SGX_FEATURE_MP)
-#endif 
+//     IMG_UINT32 ui32MasterClkGateStatusReg;
+//     IMG_UINT32 ui32MasterClkGateStatusMask;
+//     IMG_UINT32 ui32MasterClkGateStatus2Reg;
+//     IMG_UINT32 ui32MasterClkGateStatus2Mask;
+#endif /* SGX_FEATURE_MP */
 
        IMG_UINT32 ui32CacheControl;
 
@@ -400,7 +430,7 @@ typedef struct _SGX_CCB_KICK_KM_
        IMG_UINT32      ui32NumDstSyncObjects;
        IMG_HANDLE      hKernelHWSyncListMemInfo;
 
-       
+       /* DST syncs */
        IMG_HANDLE      *pahDstSyncHandles;
 
        IMG_UINT32      ui32NumTAStatusVals;
@@ -415,15 +445,15 @@ typedef struct _SGX_CCB_KICK_KM_
 #endif
 
        IMG_BOOL        bFirstKickOrResume;
-#if (defined(NO_HARDWARE) || defined(PDUMP))
+#if defined(NO_HARDWARE) || defined(PDUMP)
        IMG_BOOL        bTerminateOrAbort;
 #endif
 
-       
+       /* CCB offset of data structure associated with this kick */
        IMG_UINT32      ui32CCBOffset;
 
 #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS)
-       
+       /* SRC and DST syncs */
        IMG_UINT32      ui32NumTASrcSyncs;
        IMG_HANDLE      ahTASrcKernelSyncInfo[SGX_MAX_TA_SRC_SYNCS];
        IMG_UINT32      ui32NumTADstSyncs;
@@ -431,12 +461,12 @@ typedef struct _SGX_CCB_KICK_KM_
        IMG_UINT32      ui32Num3DSrcSyncs;
        IMG_HANDLE      ah3DSrcKernelSyncInfo[SGX_MAX_3D_SRC_SYNCS];
 #else
-       
+       /* SRC syncs */
        IMG_UINT32      ui32NumSrcSyncs;
-       IMG_HANDLE      ahSrcKernelSyncInfo[SGX_MAX_SRC_SYNCS];
+       IMG_HANDLE      ahSrcKernelSyncInfo[SGX_MAX_SRC_SYNCS_TA];
 #endif
 
-       
+       /* TA/3D dependency data */
        IMG_BOOL        bTADependency;
        IMG_HANDLE      hTA3DSyncInfo;
 
@@ -487,13 +517,13 @@ typedef struct _PVRSRV_2D_SGX_KICK_KM_
        IMG_UINT32              ui32NumSrcSync;
        IMG_HANDLE              ahSrcSyncInfo[SGX_MAX_2D_SRC_SYNC_OPS];
 
-       
+       /* need to be able to check reads and writes on dest, and update writes */
        IMG_HANDLE              hDstSyncInfo;
 
-       
+       /* need to be able to check reads and writes on TA ops, and update writes */
        IMG_HANDLE              hTASyncInfo;
 
-       
+       /* need to be able to check reads and writes on 2D ops, and update writes */
        IMG_HANDLE              h3DSyncInfo;
 
        IMG_UINT32              ui32PDumpFlags;
@@ -501,9 +531,12 @@ typedef struct _PVRSRV_2D_SGX_KICK_KM_
        IMG_UINT32              ui32CCBDumpWOff;
 #endif
 } PVRSRV_2D_SGX_KICK_KM, *PPVRSRV_2D_SGX_KICK_KM;
-#endif 
-#endif 
+#endif /* defined(SGX_FEATURE_2D_HARDWARE) */
+#endif /* #if defined(TRANSFER_QUEUE) */
 
+/****************************************************************************/
+/* kernel only functions prototypes                                                                            */
+/****************************************************************************/
 PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode);
 
 IMG_VOID SGXOSTimer(IMG_VOID *pvData);
@@ -537,12 +570,18 @@ PVRSRV_ERROR SGXPostClockSpeedChange(IMG_HANDLE                           hDevHandle,
 
 IMG_VOID SGXPanic(PVRSRV_SGXDEV_INFO   *psDevInfo);
 
+IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO  *psDevInfo,
+                                                  IMG_BOOL                             bDumpSGXRegs);
+
 PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode);
 
 #if defined(SGX_DYNAMIC_TIMING_INFO)
 IMG_VOID SysGetSGXTimingInformation(SGX_TIMING_INFORMATION *psSGXTimingInfo);
 #endif
 
+/****************************************************************************/
+/* kernel only functions:                                                                                                      */
+/****************************************************************************/
 #if defined(NO_HARDWARE)
 static INLINE IMG_VOID NoHardwareGenerateEvent(PVRSRV_SGXDEV_INFO              *psDevInfo,
                                                                                                IMG_UINT32 ui32StatusRegister,
@@ -564,5 +603,8 @@ static INLINE IMG_VOID NoHardwareGenerateEvent(PVRSRV_SGXDEV_INFO           *psDevInfo,
 }
 #endif
 
-#endif 
+#endif /* __SGXINFOKM_H__ */
 
+/*****************************************************************************
+ End of file (sgxinfokm.h)
+*****************************************************************************/
index 7f83a43..4abff88 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device specific initialisation routines
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <stddef.h>
 
 #include "lists.h"
 #include "srvkm.h"
 #include "ttrace.h"
-#define VAR(x) #x
 
+#if defined(PVRSRV_USSE_EDM_STATUS_DEBUG)
+
+static const IMG_CHAR *SGXUKernelStatusString(IMG_UINT32 code)
+{
+       switch(code)
+       {
+#define MKTC_ST(x) \
+               case x: \
+                       return #x;
+#include "sgx_ukernel_status_codes.h"
+               default:
+                       return "(Unknown)";
+       }
+}
+
+#endif /* defined(PVRSRV_USSE_EDM_STATUS_DEBUG) */
+
+#define VAR(x) #x
+/* PRQA S 0881 11 */ /* ignore 'order of evaluation' warning */
 #define CHECK_SIZE(NAME) \
 {      \
        if (psSGXStructSizes->ui32Sizeof_##NAME != psDevInfo->sSGXStructSizes.ui32Sizeof_##NAME) \
@@ -76,20 +108,37 @@ static
 PVRSRV_ERROR SGXGetMiscInfoUkernel(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                                                   PVRSRV_DEVICE_NODE   *psDeviceNode,
                                                                   IMG_HANDLE hDevMemContext);
-static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO   *psDevInfo,
-                                                                 IMG_BOOL                              bDumpSGXRegs);
-
 #if defined(PDUMP)
 static
 PVRSRV_ERROR SGXResetPDump(PVRSRV_DEVICE_NODE *psDeviceNode);
 #endif
 
+/*!
+*******************************************************************************
+
+ @Function     SGXCommandComplete
+
+ @Description
+
+ SGX command complete handler
+
+ @Input psDeviceNode - SGX device node
+
+ @Return none
+
+******************************************************************************/
 static IMG_VOID SGXCommandComplete(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
 #if defined(OS_SUPPORTS_IN_LISR)
        if (OSInLISR(psDeviceNode->psSysData))
        {
-               
+               /*
+                * We shouldn't call SGXScheduleProcessQueuesKM in an
+                * LISR, as it may attempt to power up SGX.
+                * We assume that the LISR will schedule the MISR, which
+                * will test the following flag, and call
+                * SGXScheduleProcessQueuesKM if the flag is set.
+                */
                psDeviceNode->bReProcessDeviceCommandComplete = IMG_TRUE;
        }
        else
@@ -101,18 +150,47 @@ static IMG_VOID SGXCommandComplete(PVRSRV_DEVICE_NODE *psDeviceNode)
 #endif
 }
 
+/*!
+*******************************************************************************
+
+ @Function     DeinitDevInfo
+
+ @Description
+
+ Deinits DevInfo
+
+ @Input none
+
+ @Return none
+
+******************************************************************************/
 static IMG_UINT32 DeinitDevInfo(PVRSRV_SGXDEV_INFO *psDevInfo)
 {
        if (psDevInfo->psKernelCCBInfo != IMG_NULL)
        {
-               
-
+               /*
+                       Free CCB info.
+               */
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(PVRSRV_SGX_CCB_INFO), psDevInfo->psKernelCCBInfo, IMG_NULL);
        }
 
        return PVRSRV_OK;
 }
 
+/*!
+*******************************************************************************
+
+ @Function     InitDevInfo
+
+ @Description
+
+ Loads DevInfo
+
+ @Input psDeviceNode
+
+ @Return PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR InitDevInfo(PVRSRV_PER_PROCESS_DATA *psPerProc,
                                                                PVRSRV_DEVICE_NODE *psDeviceNode,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -163,7 +241,7 @@ static PVRSRV_ERROR InitDevInfo(PVRSRV_PER_PROCESS_DATA *psPerProc,
 #if defined(FIX_HW_BRN_29823)
        psDevInfo->psKernelDummyTermStreamMemInfo = (PVRSRV_KERNEL_MEM_INFO *)psInitInfo->hKernelDummyTermStreamMemInfo;
 #endif
-#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31425)
+#if defined(SGX_FEATURE_VDM_CONTEXT_SWITCH) && defined(FIX_HW_BRN_31559)
        psDevInfo->psKernelVDMSnapShotBufferMemInfo = (PVRSRV_KERNEL_MEM_INFO *)psInitInfo->hKernelVDMSnapShotBufferMemInfo;
        psDevInfo->psKernelVDMCtrlStreamBufferMemInfo = (PVRSRV_KERNEL_MEM_INFO *)psInitInfo->hKernelVDMCtrlStreamBufferMemInfo;
 #endif
@@ -174,17 +252,19 @@ static PVRSRV_ERROR InitDevInfo(PVRSRV_PER_PROCESS_DATA *psPerProc,
 #if defined(PVRSRV_USSE_EDM_STATUS_DEBUG)
        psDevInfo->psKernelEDMStatusBufferMemInfo = (PVRSRV_KERNEL_MEM_INFO *)psInitInfo->hKernelEDMStatusBufferMemInfo;
 #endif
-#if defined(SGX_FEATURE_SPM_MODE_0)
-       psDevInfo->psKernelTmpDPMStateMemInfo = (PVRSRV_KERNEL_MEM_INFO *)psInitInfo->hKernelTmpDPMStateMemInfo;
-#endif
-       
+       /*
+        *      Assign client-side build options for later verification
+        */
        psDevInfo->ui32ClientBuildOptions = psInitInfo->ui32ClientBuildOptions;
 
-       
+       /*
+        *      Assign microkernel IF structure sizes for later verification
+        */
        psDevInfo->sSGXStructSizes = psInitInfo->sSGXStructSizes;
 
-       
-
+       /*
+               Setup the kernel version of the CCB control
+       */
        eError = OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                                sizeof(PVRSRV_SGX_CCB_INFO),
                                                (IMG_VOID **)&psKernelCCBInfo, 0,
@@ -204,8 +284,9 @@ static PVRSRV_ERROR InitDevInfo(PVRSRV_PER_PROCESS_DATA *psPerProc,
        psKernelCCBInfo->pui32ReadOffset        = &psDevInfo->psKernelCCBCtl->ui32ReadOffset;
        psDevInfo->psKernelCCBInfo = psKernelCCBInfo;
 
-       
-
+       /*
+               Copy the USE code addresses for the host kick.
+       */
        OSMemCopy(psDevInfo->aui32HostKickAddr, psInitInfo->aui32HostKickAddr,
                          SGXMKIF_CMD_MAX * sizeof(psDevInfo->aui32HostKickAddr[0]));
 
@@ -224,10 +305,10 @@ static PVRSRV_ERROR InitDevInfo(PVRSRV_PER_PROCESS_DATA *psPerProc,
        psDevInfo->ui32MasterClkGateStatusMask = psInitInfo->ui32MasterClkGateStatusMask;
        psDevInfo->ui32MasterClkGateStatus2Reg = psInitInfo->ui32MasterClkGateStatus2Reg;
        psDevInfo->ui32MasterClkGateStatus2Mask = psInitInfo->ui32MasterClkGateStatus2Mask;
-#endif 
+#endif /* SGX_FEATURE_MP */
 
 
-       
+       /* Initialise Dev Data */
        OSMemCopy(&psDevInfo->asSGXDevData, &psInitInfo->asInitDevData, sizeof(psDevInfo->asSGXDevData));
 
        return PVRSRV_OK;
@@ -259,6 +340,15 @@ static PVRSRV_ERROR SGXRunScript(PVRSRV_SGXDEV_INFO *psDevInfo, SGX_INIT_COMMAND
                                PDUMPREG(SGX_PDUMPREG_NAME, psComm->sWriteHWReg.ui32Offset, psComm->sWriteHWReg.ui32Value);
                                break;
                        }
+                       case SGX_INIT_OP_READ_HW_REG:
+                       {
+                               OSReadHWReg(psDevInfo->pvRegsBaseKM, psComm->sReadHWReg.ui32Offset);
+#if defined(PDUMP)
+                               PDUMPCOMMENT("SGXRunScript: Read HW reg operation");
+                               PDumpRegRead(SGX_PDUMPREG_NAME, psComm->sReadHWReg.ui32Offset, PDUMP_FLAGS_CONTINUOUS);
+#endif
+                               break;
+                       }
 #if defined(PDUMP)
                        case SGX_INIT_OP_PDUMP_HW_REG:
                        {
@@ -272,7 +362,7 @@ static PVRSRV_ERROR SGXRunScript(PVRSRV_SGXDEV_INFO *psDevInfo, SGX_INIT_COMMAND
                                return PVRSRV_OK;
                        }
                        case SGX_INIT_OP_ILLEGAL:
-                       
+                       /* FALLTHROUGH */
                        default:
                        {
                                PVR_DPF((PVR_DBG_ERROR,"SGXRunScript: PC %d: Illegal command: %d", ui32PC, psComm->eOp));
@@ -285,6 +375,93 @@ static PVRSRV_ERROR SGXRunScript(PVRSRV_SGXDEV_INFO *psDevInfo, SGX_INIT_COMMAND
        return PVRSRV_ERROR_UNKNOWN_SCRIPT_OPERATION;
 }
 
+#if defined(SUPPORT_MEMORY_TILING)
+static PVRSRV_ERROR SGX_AllocMemTilingRangeInt(PVRSRV_SGXDEV_INFO *psDevInfo,
+                                                                                          IMG_UINT32 ui32Start,
+                                                                                          IMG_UINT32 ui32End,
+                                                                               IMG_UINT32 ui32TilingStride,
+                                                                               IMG_UINT32 *pui32RangeIndex)
+{
+       IMG_UINT32 i;
+       IMG_UINT32 ui32Offset;
+       IMG_UINT32 ui32Val;
+
+       /* HW supports 10 ranges */
+       for(i=0; i < SGX_BIF_NUM_TILING_RANGES; i++)
+       {
+               if((psDevInfo->ui32MemTilingUsage & (1U << i)) == 0)
+               {
+                       /* mark in use */
+                       psDevInfo->ui32MemTilingUsage |= 1U << i;
+                       /* output range index if the caller wants it */
+                       if(pui32RangeIndex != IMG_NULL)
+                       {
+                               *pui32RangeIndex = i;
+                       }
+                       goto RangeAllocated;
+               }
+       }
+
+       PVR_DPF((PVR_DBG_ERROR,"SGX_AllocMemTilingRange: all tiling ranges in use"));
+       return PVRSRV_ERROR_EXCEEDED_HW_LIMITS;
+
+RangeAllocated:
+
+       /* An improperly aligned range could cause BIF not to tile some memory which is intended to be tiled,
+        * or cause BIF to tile some memory which is not intended to be.
+        */
+       if(ui32Start & ~SGX_BIF_TILING_ADDR_MASK)
+       {
+               PVR_DPF((PVR_DBG_WARNING,"SGX_AllocMemTilingRangeInt: Tiling range start (0x%08X) fails"
+                                               "alignment test", ui32Start));
+       }
+       if((ui32End + 0x00001000) & ~SGX_BIF_TILING_ADDR_MASK)
+       {
+               PVR_DPF((PVR_DBG_WARNING,"SGX_AllocMemTilingRangeInt: Tiling range end (0x%08X) fails"
+                                               "alignment test", ui32End));
+       }
+
+       ui32Offset = EUR_CR_BIF_TILE0 + (i<<2);
+
+       ui32Val = ((ui32TilingStride << EUR_CR_BIF_TILE0_CFG_SHIFT) & EUR_CR_BIF_TILE0_CFG_MASK)
+                       | (((ui32End>>SGX_BIF_TILING_ADDR_LSB) << EUR_CR_BIF_TILE0_MAX_ADDRESS_SHIFT) & EUR_CR_BIF_TILE0_MAX_ADDRESS_MASK)
+                       | (((ui32Start>>SGX_BIF_TILING_ADDR_LSB) << EUR_CR_BIF_TILE0_MIN_ADDRESS_SHIFT) & EUR_CR_BIF_TILE0_MIN_ADDRESS_MASK)
+                       | (EUR_CR_BIF_TILE0_ENABLE << EUR_CR_BIF_TILE0_CFG_SHIFT);
+
+       OSWriteHWReg(psDevInfo->pvRegsBaseKM, ui32Offset, ui32Val);
+       PDUMPREG(SGX_PDUMPREG_NAME, ui32Offset, ui32Val);
+
+#if defined(SGX_FEATURE_BIF_WIDE_TILING_AND_4K_ADDRESS)
+       ui32Offset = EUR_CR_BIF_TILE0_ADDR_EXT + (i<<2);
+
+       ui32Val = (((ui32End>>SGX_BIF_TILING_EXT_ADDR_LSB) << EUR_CR_BIF_TILE0_ADDR_EXT_MAX_SHIFT) & EUR_CR_BIF_TILE0_ADDR_EXT_MAX_MASK)
+                       | (((ui32Start>>SGX_BIF_TILING_EXT_ADDR_LSB) << EUR_CR_BIF_TILE0_ADDR_EXT_MIN_SHIFT) & EUR_CR_BIF_TILE0_ADDR_EXT_MIN_MASK);
+
+       OSWriteHWReg(psDevInfo->pvRegsBaseKM, ui32Offset, ui32Val);
+       PDUMPREG(SGX_PDUMPREG_NAME, ui32Offset, ui32Val);
+#endif /* SGX_FEATURE_BIF_WIDE_TILING_AND_4K_ADDRESS */
+
+       return PVRSRV_OK;
+}
+
+#endif /* SUPPORT_MEMORY_TILING */
+
+/*!
+*******************************************************************************
+
+ @Function     SGXInitialise
+
+ @Description
+
+ (client invoked) chip-reset and initialisation
+
+ @Input pvDeviceNode - device info. structure
+ @Input bHardwareRecovery - true if recovering powered hardware,
+                                                       false if powering up
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                                   IMG_BOOL                             bHardwareRecovery)
 {
@@ -294,16 +471,17 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO     *psDevInfo,
        static IMG_BOOL                 bFirstTime = IMG_TRUE;
 #if defined(PDUMP)
        IMG_BOOL                                bPDumpIsSuspended = PDumpIsSuspended();
-#endif 
+#endif /* PDUMP */
 
 #if defined(SGX_FEATURE_MP)
-       
+       /* Slave core clocks must be enabled during reset */
 #else
        SGXInitClocks(psDevInfo, PDUMP_FLAGS_CONTINUOUS);
-#endif 
+#endif /* SGX_FEATURE_MP */
        
-       
-
+       /*
+               Part 1 of the initialisation script runs before resetting SGX.
+       */
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS, "SGX initialisation script part 1\n");
        eError = SGXRunScript(psDevInfo, psDevInfo->sScripts.asInitCommandsPart1, SGX_MAX_INIT_COMMANDS);
        if (eError != PVRSRV_OK)
@@ -313,27 +491,33 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO     *psDevInfo,
        }
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS, "End of SGX initialisation script part 1\n");
 
-       
+       /* Reset the chip */
        psDevInfo->ui32NumResets++;
-       SGXReset(psDevInfo, bFirstTime || bHardwareRecovery, PDUMP_FLAGS_CONTINUOUS);
+       
+#if !defined(SGX_FEATURE_MP)
+       bHardwareRecovery |= bFirstTime;
+#endif /* SGX_FEATURE_MP */
+       
+       SGXReset(psDevInfo, bHardwareRecovery, PDUMP_FLAGS_CONTINUOUS);
 
 #if defined(EUR_CR_POWER)
 #if defined(SGX531)
-       
-
-
-
-
+       /*
+               Disable half the pipes.
+               531 has 2 pipes within a 4 pipe framework, so 
+               the 2 redundant pipes must be disabled even
+               though they do not exist.
+       */
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_POWER, 1);
        PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_POWER, 1);
 #else
-       
+       /* set the default pipe count (all fully enabled) */
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_POWER, 0);
        PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_POWER, 0);
 #endif
 #endif
 
-       
+       /* Initialise the kernel CCB event kicker value */
        *psDevInfo->pui32KernelCCBEventKicker = 0;
 #if defined(PDUMP)
        if (!bPDumpIsSuspended)
@@ -344,10 +528,42 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO     *psDevInfo,
                                 sizeof(*psDevInfo->pui32KernelCCBEventKicker), PDUMP_FLAGS_CONTINUOUS,
                                 MAKEUNIQUETAG(psDevInfo->psKernelCCBEventKickerMemInfo));
        }
-#endif 
+#endif /* PDUMP */
 
-       
+#if defined(SUPPORT_MEMORY_TILING)
+       {
+               /* Initialise EUR_CR_BIF_TILE registers for any tiling heaps */
+               DEVICE_MEMORY_HEAP_INFO *psDeviceMemoryHeap = psDevInfo->pvDeviceMemoryHeap;
+               IMG_UINT32 i;
 
+               psDevInfo->ui32MemTilingUsage = 0;
+
+               for(i=0; i<psDevInfo->ui32HeapCount; i++)
+               {
+                       if(psDeviceMemoryHeap[i].ui32XTileStride > 0)
+                       {
+                               /* Set up the HW control registers */
+                               eError = SGX_AllocMemTilingRangeInt(
+                                               psDevInfo,
+                                               psDeviceMemoryHeap[i].sDevVAddrBase.uiAddr,
+                                               psDeviceMemoryHeap[i].sDevVAddrBase.uiAddr
+                                                       + psDeviceMemoryHeap[i].ui32HeapSize,
+                                               psDeviceMemoryHeap[i].ui32XTileStride,
+                                               NULL);
+                               if(eError != PVRSRV_OK)
+                               {
+                                       PVR_DPF((PVR_DBG_ERROR, "Unable to allocate SGX BIF tiling range for heap: %s",
+                                                                                       psDeviceMemoryHeap[i].pszName));
+                                       break;
+                               }
+                       }
+               }
+       }
+#endif
+
+       /*
+               Part 2 of the initialisation script runs after resetting SGX.
+       */
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS, "SGX initialisation script part 2\n");
        eError = SGXRunScript(psDevInfo, psDevInfo->sScripts.asInitCommandsPart2, SGX_MAX_INIT_COMMANDS);
        if (eError != PVRSRV_OK)
@@ -356,12 +572,12 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO     *psDevInfo,
                return eError;
        }
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS, "End of SGX initialisation script part 2\n");
-
        if(!(cpu_is_omap3530() || cpu_is_omap3517()))
         {
                OSWriteHWReg(psDevInfo->pvRegsBaseKM, 0xFF08, 0x80000000);//OCP Bypass mode
         }
-       
+
+       /* Record the system timestamp for the microkernel */
        psSGXHostCtl->ui32HostClock = OSClockus();
 
        psSGXHostCtl->ui32InitStatus = 0;
@@ -374,7 +590,7 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO       *psDevInfo,
                         MAKEUNIQUETAG(psSGXHostCtlMemInfo));
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS,
                                                  "Initialise the microkernel\n");
-#endif 
+#endif /* PDUMP */
 
 #if defined(SGX_FEATURE_MULTI_EVENT_KICK)
        OSWriteMemoryBarrier();
@@ -387,13 +603,14 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO     *psDevInfo,
        OSWriteHWReg(psDevInfo->pvRegsBaseKM,
                                 SGX_MP_CORE_SELECT(EUR_CR_EVENT_KICK, 0),
                                 EUR_CR_EVENT_KICK_NOW_MASK);
-#endif 
+#endif /* SGX_FEATURE_MULTI_EVENT_KICK */
 
        OSMemoryBarrier();
 
 #if defined(PDUMP)
-       
-
+       /*
+               Dump the host kick.
+       */
        if (!bPDumpIsSuspended)
        {
 #if defined(SGX_FEATURE_MULTI_EVENT_KICK)
@@ -409,13 +626,14 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO     *psDevInfo,
                                 PDUMP_FLAGS_CONTINUOUS,
                                 MAKEUNIQUETAG(psDevInfo->psKernelCCBEventKickerMemInfo));
                PDUMPREG(SGX_PDUMPREG_NAME, SGX_MP_CORE_SELECT(EUR_CR_EVENT_KICK, 0), EUR_CR_EVENT_KICK_NOW_MASK);
-#endif 
+#endif /* SGX_FEATURE_MULTI_EVENT_KICK */
        }
-#endif 
+#endif /* PDUMP */
 
 #if !defined(NO_HARDWARE)
-       
-
+       /*
+               Wait for the microkernel to finish initialising.
+       */
        if (PollForValueKM(&psSGXHostCtl->ui32InitStatus,
                                           PVRSRV_USSE_EDM_INIT_COMPLETE,
                                           PVRSRV_USSE_EDM_INIT_COMPLETE,
@@ -424,13 +642,13 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO     *psDevInfo,
                                           IMG_FALSE) != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR, "SGXInitialise: Wait for uKernel initialisation failed"));
-               #if !defined(FIX_HW_BRN_23281)
+
                SGXDumpDebugInfo(psDevInfo, IMG_FALSE);
                PVR_DBG_BREAK;
-               #endif 
+
                return PVRSRV_ERROR_RETRY;
        }
-#endif 
+#endif /* NO_HARDWARE */
 
 #if defined(PDUMP)
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS,
@@ -442,14 +660,7 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO      *psDevInfo,
                                PDUMP_POLL_OPERATOR_EQUAL,
                                PDUMP_FLAGS_CONTINUOUS,
                                MAKEUNIQUETAG(psSGXHostCtlMemInfo));
-#endif 
-
-#if defined(FIX_HW_BRN_22997) && defined(FIX_HW_BRN_23030) && defined(SGX_FEATURE_HOST_PORT)
-       
-
-
-       WorkaroundBRN22997ReadHostPort(psDevInfo);
-#endif 
+#endif /* PDUMP */
 
        PVR_ASSERT(psDevInfo->psKernelCCBCtl->ui32ReadOffset == psDevInfo->psKernelCCBCtl->ui32WriteOffset);
 
@@ -458,13 +669,27 @@ PVRSRV_ERROR SGXInitialise(PVRSRV_SGXDEV_INFO     *psDevInfo,
        return PVRSRV_OK;
 }
 
+/*!
+*******************************************************************************
+
+ @Function     SGXDeinitialise
+
+ @Description
+
+ (client invoked) chip-reset and deinitialisation
+
+ @Input hDevCookie - device info. handle
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR SGXDeinitialise(IMG_HANDLE hDevCookie)
 
 {
        PVRSRV_SGXDEV_INFO      *psDevInfo = (PVRSRV_SGXDEV_INFO *) hDevCookie;
        PVRSRV_ERROR            eError;
 
-       
+       /* Did SGXInitialise map the SGX registers in? */
        if (psDevInfo->pvRegsBaseKM == IMG_NULL)
        {
                return PVRSRV_OK;
@@ -481,6 +706,20 @@ PVRSRV_ERROR SGXDeinitialise(IMG_HANDLE hDevCookie)
 }
 
 
+/*!
+*******************************************************************************
+
+ @Function     DevInitSGXPart1
+
+ @Description
+
+ Reset and initialise Chip
+
+ @Input pvDeviceNode - device info. structure
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
 {
        IMG_HANDLE hDevMemHeap = IMG_NULL;
@@ -492,7 +731,7 @@ static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
        DEVICE_MEMORY_HEAP_INFO *psDeviceMemoryHeap = psDeviceNode->sDevMemoryInfo.psDeviceMemoryHeap;
        PVRSRV_ERROR            eError;
 
-       
+       /* pdump info about the core */
        PDUMPCOMMENT("SGX Core Version Information: %s", SGX_CORE_FRIENDLY_NAME);
        
        #if defined(SGX_FEATURE_MP)
@@ -501,7 +740,7 @@ static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
        #else
        PDUMPCOMMENT("SGX Multi-processor: %d TA cores, %d 3D cores", SGX_FEATURE_MP_CORE_COUNT_TA, SGX_FEATURE_MP_CORE_COUNT_3D);
        #endif
-       #endif 
+       #endif /* SGX_FEATURE_MP */
 
 #if (SGX_CORE_REV == 0)
        PDUMPCOMMENT("SGX Core Revision Information: head RTL");
@@ -513,12 +752,12 @@ static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
        PDUMPCOMMENT("SGX System Level Cache is present\r\n");
        #if defined(SGX_BYPASS_SYSTEM_CACHE)
        PDUMPCOMMENT("SGX System Level Cache is bypassed\r\n");
-       #endif 
-       #endif 
+       #endif /* SGX_BYPASS_SYSTEM_CACHE */
+       #endif /* SGX_FEATURE_SYSTEM_CACHE */
 
        PDUMPCOMMENT("SGX Initialisation Part 1");
 
-       
+       /* Allocate device control block */
        if(OSAllocMem( PVRSRV_OS_NON_PAGEABLE_HEAP,
                                         sizeof(PVRSRV_SGXDEV_INFO),
                                         (IMG_VOID **)&psDevInfo, IMG_NULL,
@@ -529,17 +768,18 @@ static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
        }
        OSMemSet (psDevInfo, 0, sizeof(PVRSRV_SGXDEV_INFO));
 
-       
+       /* setup info from jdisplayconfig.h (variations controlled by build) */
        psDevInfo->eDeviceType          = DEV_DEVICE_TYPE;
        psDevInfo->eDeviceClass         = DEV_DEVICE_CLASS;
 
-       
+       /* Store the devinfo as its needed by dynamically enumerated systems called from BM */
        psDeviceNode->pvDevice = (IMG_PVOID)psDevInfo;
 
-       
+       /* get heap info from the devnode */
+       psDevInfo->ui32HeapCount = psDeviceNode->sDevMemoryInfo.ui32HeapCount;
        psDevInfo->pvDeviceMemoryHeap = (IMG_VOID*)psDeviceMemoryHeap;
 
-       
+       /* create the kernel memory context */
        hKernelDevMemContext = BM_CreateContext(psDeviceNode,
                                                                                        &sPDDevPAddr,
                                                                                        IMG_NULL,
@@ -552,7 +792,7 @@ static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
 
        psDevInfo->sKernelPDDevPAddr = sPDDevPAddr;
 
-       
+       /* create the kernel, shared and shared_exported heaps */
        for(i=0; i<psDeviceNode->sDevMemoryInfo.ui32HeapCount; i++)
        {
                switch(psDeviceMemoryHeap[i].DevMemHeapType)
@@ -561,14 +801,15 @@ static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
                        case DEVICE_MEMORY_HEAP_SHARED:
                        case DEVICE_MEMORY_HEAP_SHARED_EXPORTED:
                        {
-                               
+                               /* Shared PB heap could be zero size */
                                if (psDeviceMemoryHeap[i].ui32HeapSize > 0)
                                {
                                        hDevMemHeap = BM_CreateHeap (hKernelDevMemContext,
                                                                                                &psDeviceMemoryHeap[i]);
-                                       
-
-
+                                       /*
+                                               in the case of kernel context heaps just store
+                                               the heap handle in the heap info structure
+                                       */
                                        psDeviceMemoryHeap[i].hDevMemHeap = hDevMemHeap;
                                }
                                break;
@@ -578,7 +819,7 @@ static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
 #if defined(PDUMP)
        if(hDevMemHeap)
        {
-               
+               /* set up the MMU pdump info */
                psDevInfo->sMMUAttrib = *((BM_HEAP*)hDevMemHeap)->psMMUAttrib;
        }
 #endif
@@ -592,6 +833,23 @@ static PVRSRV_ERROR DevInitSGXPart1 (IMG_VOID *pvDeviceNode)
        return PVRSRV_OK;
 }
 
+/*!
+*******************************************************************************
+
+ @Function     SGXGetInfoForSrvinitKM
+
+ @Description
+
+ Get SGX related information necessary for initilisation server
+
+ @Input hDevHandle - device handle
+       psInitInfo - pointer to structure for returned information
+
+ @Output psInitInfo - pointer to structure containing returned information
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR SGXGetInfoForSrvinitKM(IMG_HANDLE hDevHandle, PVRSRV_HEAP_INFO_KM *pasHeapInfo, IMG_DEV_PHYADDR *psPDDevPAddr)
@@ -626,6 +884,20 @@ PVRSRV_ERROR SGXGetInfoForSrvinitKM(IMG_HANDLE hDevHandle, SGX_BRIDGE_INFO_FOR_S
        return eError;
 }
 
+/*!
+*******************************************************************************
+
+ @Function     DevInitSGXPart2KM
+
+ @Description
+
+ Reset and initialise Chip
+
+ @Input pvDeviceNode - device info. structure
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR DevInitSGXPart2KM (PVRSRV_PER_PROCESS_DATA *psPerProc,
                                 IMG_HANDLE hDevHandle,
@@ -646,8 +918,9 @@ PVRSRV_ERROR DevInitSGXPart2KM (PVRSRV_PER_PROCESS_DATA *psPerProc,
        psDeviceNode = (PVRSRV_DEVICE_NODE *)hDevHandle;
        psDevInfo = (PVRSRV_SGXDEV_INFO *)psDeviceNode->pvDevice;
 
-       
-
+       /*
+               Init devinfo
+       */
        eError = InitDevInfo(psPerProc, psDeviceNode, psInitInfo);
        if (eError != PVRSRV_OK)
        {
@@ -664,14 +937,14 @@ PVRSRV_ERROR DevInitSGXPart2KM (PVRSRV_PER_PROCESS_DATA *psPerProc,
                return PVRSRV_ERROR_INIT_FAILURE;
        }
 
-       
+       /* Registers already mapped? */
        if (psSGXDeviceMap->pvRegsCpuVBase)
        {
                psDevInfo->pvRegsBaseKM = psSGXDeviceMap->pvRegsCpuVBase;
        }
        else
        {
-               
+               /* Map Regs */
                psDevInfo->pvRegsBaseKM = OSMapPhysToLin(psSGXDeviceMap->sRegsCpuPBase,
                                                                                           psSGXDeviceMap->ui32RegsSize,
                                                                                           PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
@@ -689,7 +962,7 @@ PVRSRV_ERROR DevInitSGXPart2KM (PVRSRV_PER_PROCESS_DATA *psPerProc,
 #if defined(SGX_FEATURE_HOST_PORT)
        if (psSGXDeviceMap->ui32Flags & SGX_HOSTPORT_PRESENT)
        {
-               
+               /* Map Host Port */
                psDevInfo->pvHostPortBaseKM = OSMapPhysToLin(psSGXDeviceMap->sHPCpuPBase,
                                                                                           psSGXDeviceMap->ui32HPSize,
                                                                                           PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
@@ -702,21 +975,21 @@ PVRSRV_ERROR DevInitSGXPart2KM (PVRSRV_PER_PROCESS_DATA *psPerProc,
                psDevInfo->ui32HPSize = psSGXDeviceMap->ui32HPSize;
                psDevInfo->sHPSysPAddr = psSGXDeviceMap->sHPSysPBase;
        }
-#endif
+#endif/* #ifdef SGX_FEATURE_HOST_PORT */
 
 #if defined (SYS_USING_INTERRUPTS)
 
-       
+       /* Set up ISR callback information. */
        psDeviceNode->pvISRData = psDeviceNode;
-       
+       /* ISR handler address was set up earlier */
        PVR_ASSERT(psDeviceNode->pfnDeviceISR == SGX_ISRHandler);
 
-#endif 
+#endif /* SYS_USING_INTERRUPTS */
 
-       
+       /* Prevent the microkernel being woken up before there is something to do. */
        psDevInfo->psSGXHostCtl->ui32PowerStatus |= PVRSRV_USSE_EDM_POWMAN_NO_WORK;
        eDefaultPowerState = PVRSRV_DEV_POWER_STATE_OFF;
-       
+       /* Register the device with the power manager. */
        eError = PVRSRVRegisterPowerDevice (psDeviceNode->sDevId.ui32DeviceIndex,
                                                                                &SGXPrePowerState, &SGXPostPowerState,
                                                                                &SGXPreClockSpeedChange, &SGXPostClockSpeedChange,
@@ -729,17 +1002,8 @@ PVRSRV_ERROR DevInitSGXPart2KM (PVRSRV_PER_PROCESS_DATA *psPerProc,
                return eError;
        }
 
-#if defined(FIX_HW_BRN_22997) && defined(FIX_HW_BRN_23030) && defined(SGX_FEATURE_HOST_PORT)
-       eError = WorkaroundBRN22997Alloc(psDeviceNode);
-       if (eError != PVRSRV_OK)
-       {
-               PVR_DPF((PVR_DBG_ERROR,"SGXInitialise : Failed to alloc memory for BRN22997 workaround"));
-               return eError;
-       }
-#endif 
-
 #if defined(SUPPORT_EXTERNAL_SYSTEM_CACHE)
-       
+       /* map the external system cache control registers into the SGX MMU */
        psDevInfo->ui32ExtSysCacheRegsSize = psSGXDeviceMap->ui32ExtSysCacheRegsSize;
        psDevInfo->sExtSysCacheRegsDevPBase = psSGXDeviceMap->sExtSysCacheRegsDevPBase;
        eError = MMU_MapExtSystemCacheRegs(psDeviceNode);
@@ -748,10 +1012,11 @@ PVRSRV_ERROR DevInitSGXPart2KM (PVRSRV_PER_PROCESS_DATA *psPerProc,
                PVR_DPF((PVR_DBG_ERROR,"SGXInitialise : Failed to map external system cache registers"));
                return eError;
        }
-#endif 
-
-       
+#endif /* SUPPORT_EXTERNAL_SYSTEM_CACHE */
 
+       /*
+               Initialise the Kernel CCB
+       */
        OSMemSet(psDevInfo->psKernelCCB, 0, sizeof(PVRSRV_SGX_KERNEL_CCB));
        OSMemSet(psDevInfo->psKernelCCBCtl, 0, sizeof(PVRSRV_SGX_CCB_CTL));
        OSMemSet(psDevInfo->pui32KernelCCBEventKicker, 0, sizeof(*psDevInfo->pui32KernelCCBEventKicker));
@@ -768,6 +1033,20 @@ failed_init_dev_info:
        return eError;
 }
 
+/*!
+*******************************************************************************
+
+ @Function     DevDeInitSGX
+
+ @Description
+
+ Reset and deinitialise Chip
+
+ @Input pvDeviceNode - device info. structure
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
 {
        PVRSRV_DEVICE_NODE                      *psDeviceNode = (PVRSRV_DEVICE_NODE *)pvDeviceNode;
@@ -779,7 +1058,7 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
 
        if (!psDevInfo)
        {
-               
+               /* Can happen if DevInitSGX failed */
                PVR_DPF((PVR_DBG_ERROR,"DevDeInitSGX: Null DevInfo"));
                return PVRSRV_OK;
        }
@@ -795,29 +1074,26 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
                }
                psDevInfo->hTimer = IMG_NULL;
        }
-#endif 
+#endif /* SUPPORT_HW_RECOVERY */
 
 #if defined(SUPPORT_EXTERNAL_SYSTEM_CACHE)
-       
+       /* unmap the external system cache control registers  */
        eError = MMU_UnmapExtSystemCacheRegs(psDeviceNode);
        if (eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"DevDeInitSGX: Failed to unmap ext system cache registers"));
                return eError;
        }
-#endif 
-
-#if defined(FIX_HW_BRN_22997) && defined(FIX_HW_BRN_23030) && defined(SGX_FEATURE_HOST_PORT)
-       WorkaroundBRN22997Free(psDeviceNode);
-#endif 
+#endif /* SUPPORT_EXTERNAL_SYSTEM_CACHE */
 
        MMU_BIFResetPDFree(psDevInfo);
 
-       
-
+       /*
+               DeinitDevInfo the DevInfo
+       */
        DeinitDevInfo(psDevInfo);
 
-       
+       /* Destroy heaps. */
        psDeviceMemoryHeap = (DEVICE_MEMORY_HEAP_INFO *)psDevInfo->pvDeviceMemoryHeap;
        for(ui32Heap=0; ui32Heap<psDeviceNode->sDevMemoryInfo.ui32HeapCount; ui32Heap++)
        {
@@ -836,7 +1112,7 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
                }
        }
 
-       
+       /* Destroy the kernel context. */
        eError = BM_DestroyContext(psDeviceNode->sDevMemoryInfo.pBMKernelContext, IMG_NULL);
        if (eError != PVRSRV_OK)
        {
@@ -844,7 +1120,7 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
                return eError;
        }
 
-       
+       /* remove the device from the power manager */
        eError = PVRSRVRemovePowerDevice (((PVRSRV_DEVICE_NODE*)pvDeviceNode)->sDevId.ui32DeviceIndex);
        if (eError != PVRSRV_OK)
        {
@@ -859,10 +1135,10 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
                return eError;
        }
 
-       
+       /* Only unmap the registers if they were mapped here */
        if (!psSGXDeviceMap->pvRegsCpuVBase)
        {
-               
+               /* UnMap Regs */
                if (psDevInfo->pvRegsBaseKM != IMG_NULL)
                {
                        OSUnMapPhysToLin(psDevInfo->pvRegsBaseKM,
@@ -875,7 +1151,7 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
 #if defined(SGX_FEATURE_HOST_PORT)
        if (psSGXDeviceMap->ui32Flags & SGX_HOSTPORT_PRESENT)
        {
-               
+               /* unMap Host Port */
                if (psDevInfo->pvHostPortBaseKM != IMG_NULL)
                {
                        OSUnMapPhysToLin(psDevInfo->pvHostPortBaseKM,
@@ -884,10 +1160,10 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
                                                   IMG_NULL);
                }
        }
-#endif 
+#endif /* #ifdef SGX_FEATURE_HOST_PORT */
 
 
-       
+       /* DeAllocate devinfo */
        OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                sizeof(PVRSRV_SGXDEV_INFO),
                                psDevInfo,
@@ -897,7 +1173,7 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
 
        if (psDeviceMemoryHeap != IMG_NULL)
        {
-       
+       /* Free the device memory heap info. */
                OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
                                sizeof(DEVICE_MEMORY_HEAP_INFO) * SGX_MAX_HEAP_ID,
                                psDeviceMemoryHeap,
@@ -910,6 +1186,22 @@ static PVRSRV_ERROR DevDeInitSGX (IMG_VOID *pvDeviceNode)
 
 #if defined(RESTRICTED_REGISTERS) && defined(SGX_FEATURE_MP)
 
+/*!
+*******************************************************************************
+
+ @Function     SGXDumpMasterDebugReg
+
+ @Description
+
+ Dump a single SGX debug register value
+
+ @Input psDevInfo - SGX device info
+ @Input pszName - string used for logging
+ @Input ui32RegAddr - SGX register offset
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 static IMG_VOID SGXDumpMasterDebugReg (PVRSRV_SGXDEV_INFO      *psDevInfo,
                                                                 IMG_CHAR                       *pszName,
                                                                 IMG_UINT32                     ui32RegAddr)
@@ -919,8 +1211,25 @@ static IMG_VOID SGXDumpMasterDebugReg (PVRSRV_SGXDEV_INFO *psDevInfo,
        PVR_LOG(("(HYD) %s%08X", pszName, ui32RegVal));
 }
 
-#endif 
+#endif /* defined(RESTRICTED_REGISTERS) */
+
+/*!
+*******************************************************************************
+
+ @Function     SGXDumpDebugReg
+
+ @Description
 
+ Dump a single SGX debug register value
+
+ @Input psDevInfo - SGX device info
+ @Input ui32CoreNum - processor number
+ @Input pszName - string used for logging
+ @Input ui32RegAddr - SGX register offset
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 static IMG_VOID SGXDumpDebugReg (PVRSRV_SGXDEV_INFO    *psDevInfo,
                                                                 IMG_UINT32                     ui32CoreNum,
                                                                 IMG_CHAR                       *pszName,
@@ -931,8 +1240,38 @@ static IMG_VOID SGXDumpDebugReg (PVRSRV_SGXDEV_INFO       *psDevInfo,
        PVR_LOG(("(P%u) %s%08X", ui32CoreNum, pszName, ui32RegVal));
 }
 
-static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO   *psDevInfo,
-                                                                 IMG_BOOL                              bDumpSGXRegs)
+#if defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS) || defined(FIX_HW_BRN_31620)
+static INLINE IMG_UINT32 GetDirListBaseReg(IMG_UINT32 ui32Index)
+{
+       if (ui32Index == 0)
+       {
+               return EUR_CR_BIF_DIR_LIST_BASE0;
+       }
+       else
+       {
+               return (EUR_CR_BIF_DIR_LIST_BASE1 + ((ui32Index - 1) * 0x4));
+       }
+}
+#endif
+
+/*!
+*******************************************************************************
+
+ @Function     SGXDumpDebugInfo
+
+ @Description
+
+ Dump useful debugging info
+
+ @Input psDevInfo       - SGX device info
+ @Input bDumpSGXRegs - Whether to dump SGX debug registers. Must not be done
+                                               when SGX is not powered.
+
+ @Return   IMG_VOID
+
+******************************************************************************/
+IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO  *psDevInfo,
+                                                  IMG_BOOL                             bDumpSGXRegs)
 {
        IMG_UINT32      ui32CoreNum;
 
@@ -968,12 +1307,12 @@ static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO     *psDevInfo,
 #endif
                for (ui32CoreNum = 0; ui32CoreNum < SGX_FEATURE_MP_CORE_COUNT_3D; ui32CoreNum++)
                {
-                       
+                       /* Dump HW event status */
                        SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_EVENT_STATUS:     ", EUR_CR_EVENT_STATUS);
                        SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_EVENT_STATUS2:    ", EUR_CR_EVENT_STATUS2);
                        SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_BIF_CTRL:         ", EUR_CR_BIF_CTRL);
                #if defined(EUR_CR_BIF_BANK0)
-                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_BIF_BANK0:        ", EUR_CR_BIF_BANK0);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_BIF_BANK0:        ", EUR_CR_BIF_BANK0); 
                #endif
                        SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_BIF_INT_STAT:     ", EUR_CR_BIF_INT_STAT);
                        SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_BIF_FAULT:        ", EUR_CR_BIF_FAULT);
@@ -982,16 +1321,130 @@ static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO    *psDevInfo,
                #if defined(EUR_CR_PDS_PC_BASE)
                        SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_PDS_PC_BASE:      ", EUR_CR_PDS_PC_BASE);
                #endif
+#if defined(RESTRICTED_REGISTERS)
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_BIF_BANK_SET: ", EUR_CR_BIF_BANK_SET);
+
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_CLKGATECTL: ", EUR_CR_CLKGATECTL);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_CLKGATESTATUS: ", EUR_CR_CLKGATESTATUS);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_MTE_CTRL: ", EUR_CR_MTE_CTRL);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_EVENT_OTHER_PDS_EXEC: ", EUR_CR_EVENT_OTHER_PDS_EXEC);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_EVENT_OTHER_PDS_DATA: ", EUR_CR_EVENT_OTHER_PDS_DATA);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_EVENT_OTHER_PDS_INFO: ", EUR_CR_EVENT_OTHER_PDS_INFO);
+
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_ZLS_PAGE_THRESHOLD: ", EUR_CR_DPM_ZLS_PAGE_THRESHOLD);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_TA_GLOBAL_LIST: ", EUR_CR_DPM_TA_GLOBAL_LIST);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_STATE_CONTEXT_ID: ", EUR_CR_DPM_STATE_CONTEXT_ID);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_CONTEXT_PB_BASE: ", EUR_CR_DPM_CONTEXT_PB_BASE);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_TA_ALLOC_FREE_LIST_STATUS1: ", EUR_CR_DPM_TA_ALLOC_FREE_LIST_STATUS1);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_3D_FREE_LIST_STATUS1: ", EUR_CR_DPM_3D_FREE_LIST_STATUS1);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_TA_ALLOC_FREE_LIST_STATUS2: ", EUR_CR_DPM_TA_ALLOC_FREE_LIST_STATUS2);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_3D_FREE_LIST_STATUS2: ", EUR_CR_DPM_3D_FREE_LIST_STATUS2);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_ABORT_STATUS_MTILE: ", EUR_CR_DPM_ABORT_STATUS_MTILE);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_PAGE_STATUS: ", EUR_CR_DPM_PAGE_STATUS);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_PAGE: ", EUR_CR_DPM_PAGE);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_GLOBAL_PAGE_STATUS: ", EUR_CR_DPM_GLOBAL_PAGE_STATUS);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_VDM_CONTEXT_LOAD_STATUS: ", EUR_CR_VDM_CONTEXT_LOAD_STATUS);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_VDM_CONTEXT_STORE_STATUS: ", EUR_CR_VDM_CONTEXT_STORE_STATUS);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_VDM_TASK_KICK_STATUS: ", EUR_CR_VDM_TASK_KICK_STATUS);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_VDM_CONTEXT_STORE_STATE0: ", EUR_CR_VDM_CONTEXT_STORE_STATE0);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_VDM_CONTEXT_STORE_STATE1: ", EUR_CR_VDM_CONTEXT_STORE_STATE1);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_REQUESTING: ", EUR_CR_DPM_REQUESTING);
+                       SGXDumpDebugReg(psDevInfo, ui32CoreNum, "EUR_CR_DPM_REQUESTING: ", EUR_CR_DPM_REQUESTING);
+
+#endif
                }
-       }
 
+       #if !defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS) && !defined(FIX_HW_BRN_31620)
+               {
+                       IMG_UINT32 ui32RegVal;
+                       IMG_UINT32 ui32PDDevPAddr;
+       
+                       /*
+                               If there was a SGX pagefault check the page table too see if the
+                               host thinks the fault is correct
+                       */
+                       ui32RegVal = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_INT_STAT);
+                       if (ui32RegVal & EUR_CR_BIF_INT_STAT_PF_N_RW_MASK)
+                       {
+                               ui32RegVal = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_FAULT);
+                               ui32RegVal &= EUR_CR_BIF_FAULT_ADDR_MASK;
+                               ui32PDDevPAddr = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_DIR_LIST_BASE0);
+                               ui32PDDevPAddr &= EUR_CR_BIF_DIR_LIST_BASE0_ADDR_MASK;
+                               MMU_CheckFaultAddr(psDevInfo, ui32PDDevPAddr, ui32RegVal);
+                       }
+               }
+       #else
+               {
+                       IMG_UINT32 ui32FaultAddress;
+                       IMG_UINT32 ui32Bank0;
+                       IMG_UINT32 ui32DirListIndex;
+                       IMG_UINT32 ui32PDDevPAddr;
+       
+                       ui32FaultAddress = OSReadHWReg(psDevInfo->pvRegsBaseKM,
+                                                                                       EUR_CR_BIF_FAULT);
+                       ui32FaultAddress = ui32FaultAddress & EUR_CR_BIF_FAULT_ADDR_MASK;
+       
+                       ui32Bank0 = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_BANK0);
+       
+                       /* Check the EDM's's memory context */
+                       ui32DirListIndex = (ui32Bank0 & EUR_CR_BIF_BANK0_INDEX_EDM_MASK) >> EUR_CR_BIF_BANK0_INDEX_EDM_SHIFT;
+                       ui32PDDevPAddr = OSReadHWReg(psDevInfo->pvRegsBaseKM,
+                                                                                       GetDirListBaseReg(ui32DirListIndex));
+                       PVR_LOG(("Checking EDM memory context (index = %d, PD = 0x%08x)", ui32DirListIndex, ui32PDDevPAddr));
+                       MMU_CheckFaultAddr(psDevInfo, ui32PDDevPAddr, ui32FaultAddress);
+       
+                       /* Check the TA's memory context */
+                       ui32DirListIndex = (ui32Bank0 & EUR_CR_BIF_BANK0_INDEX_TA_MASK) >> EUR_CR_BIF_BANK0_INDEX_TA_SHIFT;
+                       ui32PDDevPAddr = OSReadHWReg(psDevInfo->pvRegsBaseKM,
+                                                                                       GetDirListBaseReg(ui32DirListIndex));
+                       PVR_LOG(("Checking TA memory context (index = %d, PD = 0x%08x)", ui32DirListIndex, ui32PDDevPAddr));
+                       MMU_CheckFaultAddr(psDevInfo, ui32PDDevPAddr, ui32FaultAddress);
+       
+                       /* Check the 3D's memory context */
+                       ui32DirListIndex = (ui32Bank0 & EUR_CR_BIF_BANK0_INDEX_3D_MASK) >> EUR_CR_BIF_BANK0_INDEX_3D_SHIFT;
+                       ui32PDDevPAddr = OSReadHWReg(psDevInfo->pvRegsBaseKM,
+                                                                                       GetDirListBaseReg(ui32DirListIndex));
+                       PVR_LOG(("Checking 3D memory context (index = %d, PD = 0x%08x)", ui32DirListIndex, ui32PDDevPAddr));
+                       MMU_CheckFaultAddr(psDevInfo, ui32PDDevPAddr, ui32FaultAddress);
+       
+       #if defined(EUR_CR_BIF_BANK0_INDEX_2D_MASK)
+                       /* Check the 2D's memory context */
+                       ui32DirListIndex = (ui32Bank0 & EUR_CR_BIF_BANK0_INDEX_2D_MASK) >> EUR_CR_BIF_BANK0_INDEX_2D_SHIFT;
+                       ui32PDDevPAddr = OSReadHWReg(psDevInfo->pvRegsBaseKM,
+                                                                                       GetDirListBaseReg(ui32DirListIndex));
+                       PVR_LOG(("Checking 2D memory context (index = %d, PD = 0x%08x)", ui32DirListIndex, ui32PDDevPAddr));
+                       MMU_CheckFaultAddr(psDevInfo, ui32PDDevPAddr, ui32FaultAddress);
+       #endif
        
-
+       #if defined(EUR_CR_BIF_BANK0_INDEX_PTLA_MASK)
+                       /* Check the 2D's memory context */
+                       ui32DirListIndex = (ui32Bank0 & EUR_CR_BIF_BANK0_INDEX_PTLA_MASK) >> EUR_CR_BIF_BANK0_INDEX_PTLA_SHIFT;
+                       ui32PDDevPAddr = OSReadHWReg(psDevInfo->pvRegsBaseKM,
+                                                                                       GetDirListBaseReg(ui32DirListIndex));
+                       PVR_LOG(("Checking PTLA memory context (index = %d, PD = 0x%08x)", ui32DirListIndex, ui32PDDevPAddr));
+                       MMU_CheckFaultAddr(psDevInfo, ui32PDDevPAddr, ui32FaultAddress);
+       #endif
+       
+       #if defined(EUR_CR_BIF_BANK0_INDEX_HOST_MASK)
+                       /* Check the Host's memory context */
+                       ui32DirListIndex = (ui32Bank0 & EUR_CR_BIF_BANK0_INDEX_HOST_MASK) >> EUR_CR_BIF_BANK0_INDEX_HOST_SHIFT;
+                       ui32PDDevPAddr = OSReadHWReg(psDevInfo->pvRegsBaseKM,
+                                                                                       GetDirListBaseReg(ui32DirListIndex));
+                       PVR_LOG(("Checking Host memory context (index = %d, PD = 0x%08x)", ui32DirListIndex, ui32PDDevPAddr));
+                       MMU_CheckFaultAddr(psDevInfo, ui32PDDevPAddr, ui32FaultAddress);
+       #endif
+               }
+       #endif
+       }
+       /*
+               Dump out the outstanding queue items.
+       */
        QueueDumpDebugInfo();
 
        {
-               
-
+               /*
+                       Dump out the Host control.
+               */
                SGXMKIF_HOST_CTL        *psSGXHostCtl = psDevInfo->psSGXHostCtl;
                IMG_UINT32                      *pui32HostCtlBuffer = (IMG_UINT32 *)psSGXHostCtl;
                IMG_UINT32                      ui32LoopCounter;
@@ -1015,8 +1468,9 @@ static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO      *psDevInfo,
        }
 
        {
-               
-
+               /*
+                       Dump out the TA/3D control.
+               */
                IMG_UINT32      *pui32TA3DCtlBuffer = psDevInfo->psKernelSGXTA3DCtlMemInfo->pvLinAddrKM;
                IMG_UINT32      ui32LoopCounter;
 
@@ -1042,11 +1496,13 @@ static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO    *psDevInfo,
                ui32WriteOffset = *pui32MKTraceBuffer;
                pui32MKTraceBuffer++;
 
-               PVR_LOG(("Last SGX microkernel status code: %08X", ui32LastStatusCode));
+               PVR_LOG(("Last SGX microkernel status code: %08X %s",
+                                ui32LastStatusCode, SGXUKernelStatusString(ui32LastStatusCode)));
 
                #if defined(PVRSRV_DUMP_MK_TRACE)
-               
-
+               /*
+                       Dump the raw microkernel trace buffer to the log.
+               */
                {
                        IMG_UINT32      ui32LoopCounter;
 
@@ -1057,17 +1513,19 @@ static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO    *psDevInfo,
                                IMG_UINT32      *pui32BufPtr;
                                pui32BufPtr = pui32MKTraceBuffer +
                                                                (((ui32WriteOffset + ui32LoopCounter) % SGXMK_TRACE_BUFFER_SIZE) * 4);
-                               PVR_LOG(("\t(MKT-%X) %08X %08X %08X %08X", ui32LoopCounter,
-                                                pui32BufPtr[2], pui32BufPtr[3], pui32BufPtr[1], pui32BufPtr[0]));
+                               PVR_LOG(("\t(MKT-%X) %08X %08X %08X %08X %s", ui32LoopCounter,
+                                                pui32BufPtr[2], pui32BufPtr[3], pui32BufPtr[1], pui32BufPtr[0],
+                                                SGXUKernelStatusString(pui32BufPtr[0])));
                        }
                }
-               #endif 
+               #endif /* PVRSRV_DUMP_MK_TRACE */
        }
-       #endif 
+       #endif /* PVRSRV_USSE_EDM_STATUS_DEBUG */
 
        {
-               
-
+               /*
+                       Dump out the kernel CCB.
+               */
                PVR_LOG(("SGX Kernel CCB WO:0x%X RO:0x%X",
                                psDevInfo->psKernelCCBCtl->ui32WriteOffset,
                                psDevInfo->psKernelCCBCtl->ui32ReadOffset));
@@ -1089,7 +1547,7 @@ static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO      *psDevInfo,
                                                psCommand->ui32Data[2], psCommand->ui32Data[3]));
                        }
                }
-               #endif 
+               #endif /* PVRSRV_DUMP_KERNEL_CCB */
        }
        #if defined (TTRACE)
        PVRSRVDumpTimeTraceBuffers();
@@ -1099,6 +1557,24 @@ static IMG_VOID SGXDumpDebugInfo (PVRSRV_SGXDEV_INFO     *psDevInfo,
 
 
 #if defined(SYS_USING_INTERRUPTS) || defined(SUPPORT_HW_RECOVERY)
+/*!
+*******************************************************************************
+
+ @Function     HWRecoveryResetSGX
+
+ @Description
+
+ Resets SGX
+
+ Note: may be called from an ISR so should not call pdump.
+
+ @Input psDevInfo - dev info
+
+ @Input ui32Component - core component to reset
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 static
 IMG_VOID HWRecoveryResetSGX (PVRSRV_DEVICE_NODE *psDeviceNode,
                                                         IMG_UINT32             ui32Component,
@@ -1107,17 +1583,25 @@ IMG_VOID HWRecoveryResetSGX (PVRSRV_DEVICE_NODE *psDeviceNode,
        PVRSRV_ERROR            eError;
        PVRSRV_SGXDEV_INFO      *psDevInfo = (PVRSRV_SGXDEV_INFO*)psDeviceNode->pvDevice;
        SGXMKIF_HOST_CTL        *psSGXHostCtl = (SGXMKIF_HOST_CTL *)psDevInfo->psSGXHostCtl;
-
-       PVR_UNREFERENCED_PARAMETER(ui32Component);
-
        
+#if defined(SUPPORT_HWRECOVERY_TRACE_LIMIT)    
+       static IMG_UINT32       ui32Clockinus = 0;
+       static IMG_UINT32       ui32HWRecoveryCount=0;
+       IMG_UINT32                      ui32TempClockinus=0;
+#endif 
+       
+       PVR_UNREFERENCED_PARAMETER(ui32Component);
 
+       /*
+               Ensure that hardware recovery is serialised with any power transitions.
+       */
        eError = PVRSRVPowerLock(ui32CallerID, IMG_FALSE);
        if(eError != PVRSRV_OK)
        {
-               
-
-
+               /*
+                       Unable to obtain lock because there is already a power transition
+                       in progress.
+               */
                PVR_DPF((PVR_DBG_WARNING,"HWRecoveryResetSGX: Power transition in progress"));
                return;
        }
@@ -1125,47 +1609,74 @@ IMG_VOID HWRecoveryResetSGX (PVRSRV_DEVICE_NODE *psDeviceNode,
        psSGXHostCtl->ui32InterruptClearFlags |= PVRSRV_USSE_EDM_INTERRUPT_HWR;
 
        PVR_LOG(("HWRecoveryResetSGX: SGX Hardware Recovery triggered"));
-
+       
+#if defined(SUPPORT_HWRECOVERY_TRACE_LIMIT)    
+/*
+ *             The following defines are system specific and should be defined in
+ *             the corresponding sysconfig.h file. The values indicated are examples only.
+               SYS_SGX_HWRECOVERY_TRACE_RESET_TIME_PERIOD              5000000 //(5 Seconds)
+               SYS_SGX_MAX_HWRECOVERY_OCCURANCE_COUNT                  5
+               */
+               ui32TempClockinus = OSClockus();
+       if((ui32TempClockinus-ui32Clockinus) < SYS_SGX_HWRECOVERY_TRACE_RESET_TIME_PERIOD){
+               ui32HWRecoveryCount++;
+               if(SYS_SGX_MAX_HWRECOVERY_OCCURANCE_COUNT <= ui32HWRecoveryCount){
+                       OSPanic();      
+               }
+       }else{
+               ui32Clockinus = ui32TempClockinus;
+               SGXDumpDebugInfo(psDeviceNode->pvDevice, IMG_TRUE);
+               ui32HWRecoveryCount = 0;
+       }
+#else  
        SGXDumpDebugInfo(psDeviceNode->pvDevice, IMG_TRUE);
-
+#endif
        
+       /* Suspend pdumping. */
        PDUMPSUSPEND();
 
-       
-#if defined(FIX_HW_BRN_23281)
-       
-       for (eError = PVRSRV_ERROR_RETRY; eError == PVRSRV_ERROR_RETRY;)
-#endif 
-       {
-               eError = SGXInitialise(psDevInfo, IMG_TRUE);
-       }
+       /* Reset and re-initialise SGX. */
+       eError = SGXInitialise(psDevInfo, IMG_TRUE);
        if (eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"HWRecoveryResetSGX: SGXInitialise failed (%d)", eError));
        }
 
-       
+       /* Resume pdumping. */
        PDUMPRESUME();
 
        PVRSRVPowerUnlock(ui32CallerID);
 
-       
+       /* Send a dummy kick so that we start processing again */
        SGXScheduleProcessQueuesKM(psDeviceNode);
 
-       
-       
+       /* Flush any old commands from the queues. */
        PVRSRVProcessQueues(IMG_TRUE);
 }
-#endif 
+#endif /* #if defined(SYS_USING_INTERRUPTS) || defined(SUPPORT_HW_RECOVERY) */
 
 
 #if defined(SUPPORT_HW_RECOVERY)
+/*!
+******************************************************************************
+
+ @Function     SGXOSTimer
+
+ @Description
+
+ Timer function for SGX
+
+ @Input pvData - private data
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 IMG_VOID SGXOSTimer(IMG_VOID *pvData)
 {
        PVRSRV_DEVICE_NODE *psDeviceNode = pvData;
        PVRSRV_SGXDEV_INFO *psDevInfo = psDeviceNode->pvDevice;
        static IMG_UINT32       ui32EDMTasks = 0;
-       static IMG_UINT32       ui32LockupCounter = 0; 
+       static IMG_UINT32       ui32LockupCounter = 0; /* To prevent false positives */
        static IMG_UINT32       ui32OpenCLDelayCounter = 0;
        static IMG_UINT32       ui32NumResets = 0;
 #if defined(FIX_HW_BRN_31093)
@@ -1176,17 +1687,21 @@ IMG_VOID SGXOSTimer(IMG_VOID *pvData)
        IMG_BOOL                bLockup = IMG_FALSE;
        IMG_BOOL                bPoweredDown;
 
-       
+       /* increment a timestamp */
        psDevInfo->ui32TimeStamp++;
 
 #if defined(NO_HARDWARE)
        bPoweredDown = IMG_TRUE;
 #else
        bPoweredDown = (SGXIsDevicePowered(psDeviceNode)) ? IMG_FALSE : IMG_TRUE;
-#endif 
+#endif /* NO_HARDWARE */
 
-       
-       
+       /*
+        * Check whether EDM timer tasks are getting scheduled. If not, assume
+        * that SGX has locked up and reset the chip.
+        */
+
+       /* Check whether the timer should be running */
        if (bPoweredDown)
        {
                ui32LockupCounter = 0;
@@ -1196,7 +1711,7 @@ IMG_VOID SGXOSTimer(IMG_VOID *pvData)
        }
        else
        {
-               
+               /* The PDS timer should be running. */
                ui32CurrentEDMTasks = OSReadHWReg(psDevInfo->pvRegsBaseKM, psDevInfo->ui32EDMTaskReg0);
                if (psDevInfo->ui32EDMTaskReg1 != 0)
                {
@@ -1225,31 +1740,31 @@ IMG_VOID SGXOSTimer(IMG_VOID *pvData)
        #if defined(FIX_HW_BRN_31093)
                                if (bBRN31093Inval == IMG_FALSE)
                                {
-                                       
+                                       /* It could be a BIF hang so do a INVAL_PTE */
                #if defined(FIX_HW_BRN_29997)
                                        IMG_UINT32      ui32BIFCtrl;
-                                       
+                               /* Pause the BIF before issuing the invalidate */
                                        ui32BIFCtrl = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL);
                                        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32BIFCtrl | EUR_CR_BIF_CTRL_PAUSE_MASK);
-                                       
+                                       /* delay for 200 clocks */
                                        SGXWaitClocks(psDevInfo, 200);
                #endif
-                                       
+                                       /* Flag that we have attempt to un-block the BIF */
                                        bBRN31093Inval = IMG_TRUE;
                                        
                                        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL_INVAL, EUR_CR_BIF_CTRL_INVAL_PTE_MASK);
-                                       
+                                       /* delay for 200 clocks */
                                        SGXWaitClocks(psDevInfo, 200);
                                                
                #if defined(FIX_HW_BRN_29997)   
-                                               
+                                       /* un-pause the BIF by restoring the BIF_CTRL */        
                                        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32BIFCtrl);
                #endif
                                }
                                else
        #endif
                                {
-                               PVR_DPF((PVR_DBG_ERROR, "SGXOSTimer() detected SGX lockup (0x%x tasks)", ui32EDMTasks));
+                                       PVR_DPF((PVR_DBG_ERROR, "SGXOSTimer() detected SGX lockup (0x%x tasks)", ui32EDMTasks));
 
                                        bLockup = IMG_TRUE;
                                        (psDevInfo->psSGXHostCtl)->ui32OpenCLDelayCount = 0;
@@ -1272,24 +1787,28 @@ SGX_NoUKernel_LockUp:
        {
                SGXMKIF_HOST_CTL        *psSGXHostCtl = (SGXMKIF_HOST_CTL *)psDevInfo->psSGXHostCtl;
 
-               
+               /* increment the counter so we know the host detected the lockup */
                psSGXHostCtl->ui32HostDetectedLockups ++;
 
-               
+               /* Reset the chip and process the queues. */
                HWRecoveryResetSGX(psDeviceNode, 0, ISR_ID);
        }
 }
-#endif 
+#endif /* defined(SUPPORT_HW_RECOVERY) */
+
 
 
 #if defined(SYS_USING_INTERRUPTS)
 
+/*
+       SGX ISR Handler
+*/
 IMG_BOOL SGX_ISRHandler (IMG_VOID *pvData)
 {
        IMG_BOOL bInterruptProcessed = IMG_FALSE;
 
 
-       
+       /* Real Hardware */
        {
                IMG_UINT32 ui32EventStatus, ui32EventEnable;
                IMG_UINT32 ui32EventClear = 0;
@@ -1300,7 +1819,7 @@ IMG_BOOL SGX_ISRHandler (IMG_VOID *pvData)
                PVRSRV_DEVICE_NODE *psDeviceNode;
                PVRSRV_SGXDEV_INFO *psDevInfo;
 
-               
+               /* check for null pointers */
                if(pvData == IMG_NULL)
                {
                        PVR_DPF((PVR_DBG_ERROR, "SGX_ISRHandler: Invalid params\n"));
@@ -1313,18 +1832,20 @@ IMG_BOOL SGX_ISRHandler (IMG_VOID *pvData)
                ui32EventStatus = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_STATUS);
                ui32EventEnable = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_HOST_ENABLE);
 
-               
+               /* test only the unmasked bits */
                ui32EventStatus &= ui32EventEnable;
 
 #if defined(SGX_FEATURE_DATA_BREAKPOINTS)
                ui32EventStatus2 = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_STATUS2);
                ui32EventEnable2 = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_HOST_ENABLE2);
 
-               
+               /* test only the unmasked bits */
                ui32EventStatus2 &= ui32EventEnable2;
-#endif 
+#endif /* defined(SGX_FEATURE_DATA_BREAKPOINTS) */
 
-               
+               /* Thought: is it better to insist that the bit assignment in
+                  the "clear" register(s) matches that of the "status" register(s)?
+                  It would greatly simplify this LISR */
 
                if (ui32EventStatus & EUR_CR_EVENT_STATUS_SW_EVENT_MASK)
                {
@@ -1341,16 +1862,16 @@ IMG_BOOL SGX_ISRHandler (IMG_VOID *pvData)
                {
                        ui32EventClear2 |= EUR_CR_EVENT_HOST_CLEAR2_DATA_BREAKPOINT_TRAPPED_MASK;
                }
-#endif 
+#endif /* defined(SGX_FEATURE_DATA_BREAKPOINTS) */
 
                if (ui32EventClear || ui32EventClear2)
                {
                        bInterruptProcessed = IMG_TRUE;
 
-                       
+                       /* Clear master interrupt bit */
                        ui32EventClear |= EUR_CR_EVENT_HOST_CLEAR_MASTER_INTERRUPT_MASK;
 
-                       
+                       /* clear the events */
                        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_HOST_CLEAR, ui32EventClear);
                        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_HOST_CLEAR2, ui32EventClear2);
                }
@@ -1360,6 +1881,9 @@ IMG_BOOL SGX_ISRHandler (IMG_VOID *pvData)
 }
 
 
+/*
+       SGX MISR Handler
+*/
 static IMG_VOID SGX_MISRHandler (IMG_VOID *pvData)
 {
        PVRSRV_DEVICE_NODE      *psDeviceNode = (PVRSRV_DEVICE_NODE *)pvData;
@@ -1381,80 +1905,27 @@ static IMG_VOID SGX_MISRHandler (IMG_VOID *pvData)
 
        SGXTestActivePowerEvent(psDeviceNode, ISR_ID);
 }
-#endif 
-
-
+#endif /* #if defined (SYS_USING_INTERRUPTS) */
 
 #if defined(SUPPORT_MEMORY_TILING)
+
+IMG_INTERNAL
 PVRSRV_ERROR SGX_AllocMemTilingRange(PVRSRV_DEVICE_NODE *psDeviceNode,
-                                                                               PVRSRV_KERNEL_MEM_INFO  *psMemInfo,
-                                                                               IMG_UINT32 ui32TilingStride,
-                                                                               IMG_UINT32 *pui32RangeIndex)
+                                                                        PVRSRV_KERNEL_MEM_INFO *psMemInfo,
+                                                                        IMG_UINT32 ui32XTileStride,
+                                                                        IMG_UINT32 *pui32RangeIndex)
 {
-#if defined(SGX_FEATURE_BIF_WIDE_TILING_AND_4K_ADDRESS)
-       PVRSRV_SGXDEV_INFO *psDevInfo = psDeviceNode->pvDevice;
-       IMG_UINT32 i;
-       IMG_UINT32 ui32Start;
-       IMG_UINT32 ui32End;
-       IMG_UINT32 ui32Offset;
-       IMG_UINT32 ui32Val;
-
-       
-       for(i=0; i<10; i++)
-       {
-               if((psDevInfo->ui32MemTilingUsage & (1U << i)) == 0)
-               {
-                       
-                       psDevInfo->ui32MemTilingUsage |= 1U << i;
-                       
-                       *pui32RangeIndex = i;
-                       goto RangeAllocated;
-               }
-       }
-
-       PVR_DPF((PVR_DBG_ERROR,"SGX_AllocMemTilingRange: all tiling ranges in use"));
-       return PVRSRV_ERROR_EXCEEDED_HW_LIMITS;
-
-RangeAllocated:
-       ui32Offset = EUR_CR_BIF_TILE0 + (i<<2);
-
-       ui32Start = psMemInfo->sDevVAddr.uiAddr;
-       ui32End = ui32Start + psMemInfo->uAllocSize + SGX_MMU_PAGE_SIZE - 1;
-
-       ui32Val = ((ui32TilingStride << EUR_CR_BIF_TILE0_CFG_SHIFT) & EUR_CR_BIF_TILE0_CFG_MASK)
-                       | (((ui32End>>20) << EUR_CR_BIF_TILE0_MAX_ADDRESS_SHIFT) & EUR_CR_BIF_TILE0_MAX_ADDRESS_MASK)
-                       | (((ui32Start>>20) << EUR_CR_BIF_TILE0_MIN_ADDRESS_SHIFT) & EUR_CR_BIF_TILE0_MIN_ADDRESS_MASK)
-                       | (0x8 << EUR_CR_BIF_TILE0_CFG_SHIFT);
-
-       
-       OSWriteHWReg(psDevInfo->pvRegsBaseKM, ui32Offset, ui32Val);
-       PDUMPREG(SGX_PDUMPREG_NAME, ui32Offset, ui32Val);
-
-       ui32Offset = EUR_CR_BIF_TILE0_ADDR_EXT + (i<<2);
-
-       ui32Val = (((ui32End>>12) << EUR_CR_BIF_TILE0_ADDR_EXT_MAX_SHIFT) & EUR_CR_BIF_TILE0_ADDR_EXT_MAX_MASK)
-                       | (((ui32Start>>12) << EUR_CR_BIF_TILE0_ADDR_EXT_MIN_SHIFT) & EUR_CR_BIF_TILE0_ADDR_EXT_MIN_MASK);
-
-       
-       OSWriteHWReg(psDevInfo->pvRegsBaseKM, ui32Offset, ui32Val);
-       PDUMPREG(SGX_PDUMPREG_NAME, ui32Offset, ui32Val);
-
-       return PVRSRV_OK;
-#else
-       PVR_UNREFERENCED_PARAMETER(psDeviceNode);
-       PVR_UNREFERENCED_PARAMETER(psMemInfo);
-       PVR_UNREFERENCED_PARAMETER(ui32TilingStride);
-       PVR_UNREFERENCED_PARAMETER(pui32RangeIndex);
-
-       PVR_DPF((PVR_DBG_ERROR,"SGX_AllocMemTilingRange: device does not support memory tiling"));
-       return PVRSRV_ERROR_NOT_SUPPORTED;
-#endif
+       return SGX_AllocMemTilingRangeInt(psDeviceNode->pvDevice,
+               psMemInfo->sDevVAddr.uiAddr,
+               psMemInfo->sDevVAddr.uiAddr + ((IMG_UINT32) psMemInfo->uAllocSize) + SGX_MMU_PAGE_SIZE - 1,
+               ui32XTileStride,
+               pui32RangeIndex);
 }
 
+IMG_INTERNAL
 PVRSRV_ERROR SGX_FreeMemTilingRange(PVRSRV_DEVICE_NODE *psDeviceNode,
                                                                                IMG_UINT32 ui32RangeIndex)
 {
-#if defined(SGX_FEATURE_BIF_WIDE_TILING_AND_4K_ADDRESS)
        PVRSRV_SGXDEV_INFO *psDevInfo = psDeviceNode->pvDevice;
        IMG_UINT32 ui32Offset;
        IMG_UINT32 ui32Val;
@@ -1465,27 +1936,21 @@ PVRSRV_ERROR SGX_FreeMemTilingRange(PVRSRV_DEVICE_NODE *psDeviceNode,
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
 
-       
+       /* clear the usage bit */
        psDevInfo->ui32MemTilingUsage &= ~(1<<ui32RangeIndex);
 
-       
+       /* disable the range */
        ui32Offset = EUR_CR_BIF_TILE0 + (ui32RangeIndex<<2);
        ui32Val = 0;
 
-       
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, ui32Offset, ui32Val);
        PDUMPREG(SGX_PDUMPREG_NAME, ui32Offset, ui32Val);
 
        return PVRSRV_OK;
-#else
-       PVR_UNREFERENCED_PARAMETER(psDeviceNode);
-       PVR_UNREFERENCED_PARAMETER(ui32RangeIndex);
-
-       PVR_DPF((PVR_DBG_ERROR,"SGX_FreeMemTilingRange: device does not support memory tiling"));
-       return PVRSRV_ERROR_NOT_SUPPORTED;
-#endif
 }
-#endif
+
+#endif /* defined(SUPPORT_MEMORY_TILING) */
+
 
 static IMG_VOID SGXCacheInvalidate(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
@@ -1495,20 +1960,34 @@ static IMG_VOID SGXCacheInvalidate(PVRSRV_DEVICE_NODE *psDeviceNode)
        psDevInfo->ui32CacheControl |= SGXMKIF_CC_INVAL_BIF_SL;
        #else
        PVR_UNREFERENCED_PARAMETER(psDevInfo);
-       #endif 
+       #endif /* SGX_FEATURE_MP */
 }
 
+/*!
+*******************************************************************************
+
+ @Function     SGXRegisterDevice
+
+ @Description
+
+ Registers the device with the system
+
+ @Input:       psDeviceNode - device node
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        DEVICE_MEMORY_INFO *psDevMemoryInfo;
        DEVICE_MEMORY_HEAP_INFO *psDeviceMemoryHeap;
 
-       
+       /* setup details that never change */
        psDeviceNode->sDevId.eDeviceType                = DEV_DEVICE_TYPE;
        psDeviceNode->sDevId.eDeviceClass               = DEV_DEVICE_CLASS;
 #if defined(PDUMP)
        {
-               
+               /* memory space names are set up in system code */
                SGX_DEVICE_MAP *psSGXDeviceMemMap;
                SysGetDeviceMemoryMap(PVRSRV_DEVICE_TYPE_SGX,
                                                          (IMG_VOID**)&psSGXDeviceMemMap);
@@ -1518,7 +1997,7 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        }
        
        psDeviceNode->sDevId.pszPDumpRegName    = SGX_PDUMPREG_NAME;
-#endif 
+#endif /* PDUMP */
 
        psDeviceNode->pfnInitDevice             = &DevInitSGXPart1;
        psDeviceNode->pfnDeInitDevice   = &DevDeInitSGX;
@@ -1528,8 +2007,9 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceNode->pfnPDumpInitDevice = &SGXResetPDump;
        psDeviceNode->pfnMMUGetContextID = &MMU_GetPDumpContextID;
 #endif
-       
-
+       /*
+               MMU callbacks
+       */
        psDeviceNode->pfnMMUInitialise = &MMU_Initialise;
        psDeviceNode->pfnMMUFinalise = &MMU_Finalise;
        psDeviceNode->pfnMMUInsertHeap = &MMU_InsertHeap;
@@ -1553,9 +2033,13 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceNode->pfnMMUGetCacheFlushRange = IMG_NULL;
        psDeviceNode->pfnMMUGetPDPhysAddr = IMG_NULL;
 #endif
-#if defined (SYS_USING_INTERRUPTS)
-       
+       psDeviceNode->pfnMMUMapPagesSparse = &MMU_MapPagesSparse;
+       psDeviceNode->pfnMMUMapShadowSparse = &MMU_MapShadowSparse;
 
+#if defined (SYS_USING_INTERRUPTS)
+       /*
+               SGX ISR handler
+       */
        psDeviceNode->pfnDeviceISR = SGX_ISRHandler;
        psDeviceNode->pfnDeviceMISR = SGX_MISRHandler;
 #endif
@@ -1565,22 +2049,24 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceNode->pfnFreeMemTilingRange = SGX_FreeMemTilingRange;
 #endif
 
-       
-
+       /*
+               SGX command complete handler
+       */
        psDeviceNode->pfnDeviceCommandComplete = &SGXCommandComplete;
 
        psDeviceNode->pfnCacheInvalidate = SGXCacheInvalidate;
 
-       
-
+       /*
+               and setup the device's memory map:
+       */
        psDevMemoryInfo = &psDeviceNode->sDevMemoryInfo;
-       
+       /* size of address space */
        psDevMemoryInfo->ui32AddressSpaceSizeLog2 = SGX_FEATURE_ADDRESS_SPACE_SIZE;
 
-       
+       /* flags, backing store details to be specified by system */
        psDevMemoryInfo->ui32Flags = 0;
 
-       
+       /* device memory heap info about each heap in a device address space */
        if(OSAllocMem( PVRSRV_OS_PAGEABLE_HEAP,
                                         sizeof(DEVICE_MEMORY_HEAP_INFO) * SGX_MAX_HEAP_ID,
                                         (IMG_VOID **)&psDevMemoryInfo->psDeviceMemoryHeap, 0,
@@ -1593,10 +2079,12 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
 
        psDeviceMemoryHeap = psDevMemoryInfo->psDeviceMemoryHeap;
 
-       
-
+       /*
+               setup heaps
+               Note: backing store to be setup by system (defaults to UMA)
+       */
 
-       
+       /************* general ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_GENERAL_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_GENERAL_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_GENERAL_HEAP_SIZE;
@@ -1606,16 +2094,50 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "General";
        psDeviceMemoryHeap->pszBSName = "General BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
 #if !defined(SUPPORT_SGX_GENERAL_MAPPING_HEAP)
-       
+       /* specify the mapping heap ID for this device */
        psDevMemoryInfo->ui32MappingHeapID = (IMG_UINT32)(psDeviceMemoryHeap - psDevMemoryInfo->psDeviceMemoryHeap);
 #endif
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
+#if defined(SUPPORT_MEMORY_TILING)
+       /************* VPB tiling ***************/
+       psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_VPB_TILED_HEAP_ID);
+       psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_VPB_TILED_HEAP_BASE;
+       psDeviceMemoryHeap->ui32HeapSize = SGX_VPB_TILED_HEAP_SIZE;
+       psDeviceMemoryHeap->ui32Attribs = PVRSRV_HAP_WRITECOMBINE
+                                                                                                               | PVRSRV_MEM_RAM_BACKED_ALLOCATION
+                                                                                                               | PVRSRV_HAP_SINGLE_PROCESS;
+       psDeviceMemoryHeap->pszName = "VPB Tiled";
+       psDeviceMemoryHeap->pszBSName = "VPB Tiled BS";
+       psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
+       /* set the default (4k). System can override these as required */
+       psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
+       psDeviceMemoryHeap->ui32XTileStride = SGX_VPB_TILED_HEAP_STRIDE;
+       PVR_DPF((PVR_DBG_WARNING, "VPB tiling heap tiling stride = 0x%x", psDeviceMemoryHeap->ui32XTileStride));
+       psDeviceMemoryHeap++;/* advance to the next heap */
+#endif
 
-       
+#if defined(SUPPORT_ION)
+       /************* Ion Heap ***************/
+       psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_ION_HEAP_ID);
+       psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_ION_HEAP_BASE;
+       psDeviceMemoryHeap->ui32HeapSize = SGX_ION_HEAP_SIZE;
+       psDeviceMemoryHeap->ui32Attribs = PVRSRV_HAP_WRITECOMBINE
+                                                                                                               | PVRSRV_HAP_SINGLE_PROCESS;
+       psDeviceMemoryHeap->pszName = "Ion";
+       psDeviceMemoryHeap->pszBSName = "Ion BS";
+       psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
+       /* specify the ion heap ID for this device */
+       psDevMemoryInfo->ui32IonHeapID = SGX_ION_HEAP_ID;
+       /* set the default (4k). System can override these as required */
+       psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
+       psDeviceMemoryHeap++;/* advance to the next heap */
+#endif
+
+       /************* TA data ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_TADATA_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_TADATA_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_TADATA_HEAP_SIZE;
@@ -1625,12 +2147,12 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "TA Data";
        psDeviceMemoryHeap->pszBSName = "TA Data BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
-       
+       /************* kernel code ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_KERNEL_CODE_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_KERNEL_CODE_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_KERNEL_CODE_HEAP_SIZE;
@@ -1640,12 +2162,12 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "Kernel Code";
        psDeviceMemoryHeap->pszBSName = "Kernel Code BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_SHARED_EXPORTED;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
-       
+       /************* Kernel Video Data ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_KERNEL_DATA_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_KERNEL_DATA_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_KERNEL_DATA_HEAP_SIZE;
@@ -1655,20 +2177,21 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "KernelData";
        psDeviceMemoryHeap->pszBSName = "KernelData BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_SHARED_EXPORTED;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
-       
+       /************* PixelShaderUSSE ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_PIXELSHADER_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_PIXELSHADER_HEAP_BASE;
-       
-
-
-
-
-
+       /*
+               The actual size of the pixel and vertex shader heap must be such that all
+               addresses are within range of the one of the USSE code base registers, but
+               the addressable range is hardware-dependent.
+               SGX_PIXELSHADER_HEAP_SIZE is defined to be the maximum possible size
+               to ensure that the heap layout is consistent across all SGXs.
+        */
        psDeviceMemoryHeap->ui32HeapSize = ((10 << SGX_USE_CODE_SEGMENT_RANGE_BITS) - 0x00001000);
        PVR_ASSERT(psDeviceMemoryHeap->ui32HeapSize <= SGX_PIXELSHADER_HEAP_SIZE);
        psDeviceMemoryHeap->ui32Attribs = PVRSRV_HAP_WRITECOMBINE
@@ -1677,15 +2200,15 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "PixelShaderUSSE";
        psDeviceMemoryHeap->pszBSName = "PixelShaderUSSE BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
-       
+       /************* VertexShaderUSSE ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_VERTEXSHADER_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_VERTEXSHADER_HEAP_BASE;
-       
+       /* See comment above with PixelShaderUSSE ui32HeapSize */
        psDeviceMemoryHeap->ui32HeapSize = ((4 << SGX_USE_CODE_SEGMENT_RANGE_BITS) - 0x00001000);
        PVR_ASSERT(psDeviceMemoryHeap->ui32HeapSize <= SGX_VERTEXSHADER_HEAP_SIZE);
        psDeviceMemoryHeap->ui32Attribs = PVRSRV_HAP_WRITECOMBINE
@@ -1694,12 +2217,12 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "VertexShaderUSSE";
        psDeviceMemoryHeap->pszBSName = "VertexShaderUSSE BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
-       
+       /************* PDS Pixel Code/Data ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_PDSPIXEL_CODEDATA_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_PDSPIXEL_CODEDATA_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_PDSPIXEL_CODEDATA_HEAP_SIZE;
@@ -1709,12 +2232,12 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "PDSPixelCodeData";
        psDeviceMemoryHeap->pszBSName = "PDSPixelCodeData BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
-       
+       /************* PDS Vertex Code/Data ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_PDSVERTEX_CODEDATA_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_PDSVERTEX_CODEDATA_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_PDSVERTEX_CODEDATA_HEAP_SIZE;
@@ -1724,12 +2247,12 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "PDSVertexCodeData";
        psDeviceMemoryHeap->pszBSName = "PDSVertexCodeData BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
-       
+       /************* CacheCoherent ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_SYNCINFO_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_SYNCINFO_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_SYNCINFO_HEAP_SIZE;
@@ -1739,14 +2262,14 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "CacheCoherent";
        psDeviceMemoryHeap->pszBSName = "CacheCoherent BS";
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_SHARED_EXPORTED;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       
+       /* set the sync heap id */
        psDevMemoryInfo->ui32SyncHeapID = (IMG_UINT32)(psDeviceMemoryHeap - psDevMemoryInfo->psDeviceMemoryHeap);
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
-       
+       /************* Shared 3D Parameters ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_SHARED_3DPARAMETERS_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_SHARED_3DPARAMETERS_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_SHARED_3DPARAMETERS_HEAP_SIZE;
@@ -1757,11 +2280,11 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
                                                                                                        | PVRSRV_HAP_MULTI_PROCESS;
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_SHARED_EXPORTED;
 
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
-       
+       /************* Percontext 3D Parameters ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_PERCONTEXT_3DPARAMETERS_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_PERCONTEXT_3DPARAMETERS_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_PERCONTEXT_3DPARAMETERS_HEAP_SIZE;
@@ -1771,13 +2294,13 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
                                                                                                                        | PVRSRV_MEM_RAM_BACKED_ALLOCATION
                                                                                                                        | PVRSRV_HAP_SINGLE_PROCESS;
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
+       psDeviceMemoryHeap++;/* advance to the next heap */
 
 
 #if defined(SUPPORT_SGX_GENERAL_MAPPING_HEAP)
-       
+       /************* General Mapping ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_GENERAL_MAPPING_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_GENERAL_MAPPING_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_GENERAL_MAPPING_HEAP_SIZE;
@@ -1787,28 +2310,29 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
        psDeviceMemoryHeap->pszName = "GeneralMapping";
        psDeviceMemoryHeap->pszBSName = "GeneralMapping BS";
        #if defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS) && defined(FIX_HW_BRN_23410)
-       
-
-
-
-
-
-
+       /*
+               if((2D hardware is enabled)
+               && (multi-mem contexts enabled)
+               && (BRN23410 is present))
+                       - then don't make the heap per-context otherwise
+                       the TA and 2D requestors must always be aligned to
+                       the same address space which could affect performance
+       */
                psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_SHARED_EXPORTED;
-       #else 
+       #else /* defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS) && defined(FIX_HW_BRN_23410) */
                psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       #endif 
+       #endif /* defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS) && defined(FIX_HW_BRN_23410) */
 
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       
+       /* specify the mapping heap ID for this device */
        psDevMemoryInfo->ui32MappingHeapID = (IMG_UINT32)(psDeviceMemoryHeap - psDevMemoryInfo->psDeviceMemoryHeap);
-       psDeviceMemoryHeap++;
-#endif 
+       psDeviceMemoryHeap++;/* advance to the next heap */
+#endif /* #if defined(SUPPORT_SGX_GENERAL_MAPPING_HEAP) */
 
 
 #if defined(SGX_FEATURE_2D_HARDWARE)
-       
+       /************* 2D HW Heap ***************/
        psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_2D_HEAP_ID);
        psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_2D_HEAP_BASE;
        psDeviceMemoryHeap->ui32HeapSize = SGX_2D_HEAP_SIZE;
@@ -1817,33 +2341,14 @@ PVRSRV_ERROR SGXRegisterDevice (PVRSRV_DEVICE_NODE *psDeviceNode)
                                                                                                                | PVRSRV_HAP_SINGLE_PROCESS;
        psDeviceMemoryHeap->pszName = "2D";
        psDeviceMemoryHeap->pszBSName = "2D BS";
-       
        psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_SHARED_EXPORTED;
-       
+       /* set the default (4k). System can override these as required */
        psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
-#endif 
-
-
-#if defined(FIX_HW_BRN_26915)
-       
-       
-       psDeviceMemoryHeap->ui32HeapID = HEAP_ID( PVRSRV_DEVICE_TYPE_SGX, SGX_CGBUFFER_HEAP_ID);
-       psDeviceMemoryHeap->sDevVAddrBase.uiAddr = SGX_CGBUFFER_HEAP_BASE;
-       psDeviceMemoryHeap->ui32HeapSize = SGX_CGBUFFER_HEAP_SIZE;
-       psDeviceMemoryHeap->ui32Attribs = PVRSRV_HAP_WRITECOMBINE
-                                                                                                               | PVRSRV_MEM_RAM_BACKED_ALLOCATION
-                                                                                                               | PVRSRV_HAP_SINGLE_PROCESS;
-       psDeviceMemoryHeap->pszName = "CGBuffer";
-       psDeviceMemoryHeap->pszBSName = "CGBuffer BS";
+       psDeviceMemoryHeap++;/* advance to the next heap */
+#endif /* #if defined(SGX_FEATURE_2D_HARDWARE) */
 
-       psDeviceMemoryHeap->DevMemHeapType = DEVICE_MEMORY_HEAP_PERCONTEXT;
-       
-       psDeviceMemoryHeap->ui32DataPageSize = SGX_MMU_PAGE_SIZE;
-       psDeviceMemoryHeap++;
-#endif 
 
-       
+       /* set the heap count */
        psDevMemoryInfo->ui32HeapCount = (IMG_UINT32)(psDeviceMemoryHeap - psDevMemoryInfo->psDeviceMemoryHeap);
 
        return PVRSRV_OK;
@@ -1859,32 +2364,64 @@ PVRSRV_ERROR SGXResetPDump(PVRSRV_DEVICE_NODE *psDeviceNode)
        
        return PVRSRV_OK;
 }
-#endif 
+#endif /* PDUMP */
+
+
+/*!
+*******************************************************************************
+
+ @Function     SGXGetClientInfoKM
+
+ @Description  Gets the client information
 
+ @Input hDevCookie
 
+ @Output psClientInfo
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR SGXGetClientInfoKM(IMG_HANDLE                                     hDevCookie,
                                                                SGX_CLIENT_INFO*                psClientInfo)
 {
        PVRSRV_SGXDEV_INFO *psDevInfo = (PVRSRV_SGXDEV_INFO *)((PVRSRV_DEVICE_NODE *)hDevCookie)->pvDevice;
 
-       
-
+       /*
+               If this is the first client to connect to SGX perform initialisation
+       */
        psDevInfo->ui32ClientRefCount++;
 
-       
-
+       /*
+               Copy information to the client info.
+       */
        psClientInfo->ui32ProcessID = OSGetCurrentProcessIDKM();
 
-       
-
+       /*
+               Copy requested information.
+       */
        OSMemCopy(&psClientInfo->asDevData, &psDevInfo->asSGXDevData, sizeof(psClientInfo->asDevData));
 
-       
+       /* just return OK */
        return PVRSRV_OK;
 }
 
 
+/*!
+*******************************************************************************
+
+ @Function     SGXPanic
+
+ @Description
+
+ Called when an unrecoverable situation is detected. Dumps SGX debug
+ information and tells the OS to panic.
+
+ @Input psDevInfo - SGX device info
+
+ @Return IMG_VOID
+
+******************************************************************************/
 IMG_VOID SGXPanic(PVRSRV_SGXDEV_INFO   *psDevInfo)
 {
        PVR_LOG(("SGX panic"));
@@ -1893,6 +2430,21 @@ IMG_VOID SGXPanic(PVRSRV_SGXDEV_INFO     *psDevInfo)
 }
 
 
+/*!
+*******************************************************************************
+
+ @Function     SGXDevInitCompatCheck
+
+ @Description
+
+ Check compatibility of host driver and microkernel (DDK and build options)
+ for SGX devices at services/device initialisation
+
+ @Input psDeviceNode - device node
+
+ @Return   PVRSRV_ERROR - depending on mismatch found
+
+******************************************************************************/
 PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        PVRSRV_ERROR    eError;
@@ -1900,12 +2452,12 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
        IMG_UINT32                      ui32BuildOptions, ui32BuildOptionsMismatch;
 #if !defined(NO_HARDWARE)
        PPVRSRV_KERNEL_MEM_INFO                 psMemInfo;
-       PVRSRV_SGX_MISCINFO_INFO                *psSGXMiscInfoInt;      
+       PVRSRV_SGX_MISCINFO_INFO                *psSGXMiscInfoInt;      /*!< internal misc info for ukernel */
        PVRSRV_SGX_MISCINFO_FEATURES    *psSGXFeatures;
-       SGX_MISCINFO_STRUCT_SIZES               *psSGXStructSizes;      
+       SGX_MISCINFO_STRUCT_SIZES               *psSGXStructSizes;      /*!< microkernel structure sizes */
        IMG_BOOL                                                bStructSizesFailed;
 
-       
+       /* Exceptions list for core rev check, format is pairs of (hw rev, sw rev) */
        IMG_BOOL        bCheckCoreRev;
        const IMG_UINT32 aui32CoreRevExceptions[] =
        {
@@ -1915,7 +2467,7 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
        IMG_UINT        i;
 #endif
 
-       
+       /* Ensure it's a SGX device */
        if(psDeviceNode->sDevId.eDeviceType != PVRSRV_DEVICE_TYPE_SGX)
        {
                PVR_LOG(("(FAIL) SGXInit: Device not of type SGX"));
@@ -1925,8 +2477,16 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
 
        psDevInfo = psDeviceNode->pvDevice;
 
-       
-       
+       /*
+        *  1. Check kernel-side and client-side build options
+        *      2. Ensure ukernel DDK version and driver DDK version are compatible
+        *      3. Check ukernel build options against kernel-side build options
+        */
+
+       /*
+        * Check KM build options against client-side host driver
+        */
+
        ui32BuildOptions = (SGX_BUILD_OPTIONS);
        if (ui32BuildOptions != psDevInfo->ui32ClientBuildOptions)
        {
@@ -1955,13 +2515,15 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
 #if !defined (NO_HARDWARE)
        psMemInfo = psDevInfo->psKernelSGXMiscMemInfo;
 
-       
+       /* Clear state (not strictly necessary since this is the first call) */
        psSGXMiscInfoInt = psMemInfo->pvLinAddrKM;
        psSGXMiscInfoInt->ui32MiscInfoFlags = 0;
        psSGXMiscInfoInt->ui32MiscInfoFlags |= PVRSRV_USSE_MISCINFO_GET_STRUCT_SIZES;
        eError = SGXGetMiscInfoUkernel(psDevInfo, psDeviceNode, IMG_NULL);
 
-       
+       /*
+        * Validate DDK version
+        */
        if(eError != PVRSRV_OK)
        {
                PVR_LOG(("(FAIL) SGXInit: Unable to validate device DDK version"));
@@ -1977,7 +2539,6 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
                PVR_LOG(("(FAIL) SGXInit: Incompatible driver DDK revision (%d)/device DDK revision (%d).",
                                PVRVERSION_BUILD, psSGXFeatures->ui32DDKBuild));
                eError = PVRSRV_ERROR_DDK_VERSION_MISMATCH;
-               PVR_DBG_BREAK;
                goto chk_exit;
        }
        else
@@ -1986,17 +2547,22 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
                                PVRVERSION_BUILD, psSGXFeatures->ui32DDKBuild));
        }
 
-       
+       /*
+        *      Check hardware core revision is compatible with the one in software
+        */
        if (psSGXFeatures->ui32CoreRevSW == 0)
        {
-               
-
+               /*
+                       Head core revision cannot be checked.
+               */
                PVR_LOG(("SGXInit: HW core rev (%x) check skipped.",
                                psSGXFeatures->ui32CoreRev));
        }
        else
        {
-               
+               /* For some cores the hw/sw core revisions are expected not to match. For these
+                * exceptional cases the core rev compatibility check should be skipped.
+                */
                bCheckCoreRev = IMG_TRUE;
                for(i=0; i<ui32NumCoreExceptions; i+=2)
                {
@@ -2027,7 +2593,9 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
                }
        }
 
-       
+       /*
+        *      Check ukernel structure sizes are the same as those in the driver
+        */
        psSGXStructSizes = &((PVRSRV_SGX_MISCINFO_INFO*)(psMemInfo->pvLinAddrKM))->sSGXStructSizes;
 
        bStructSizesFailed = IMG_FALSE;
@@ -2062,7 +2630,10 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
                PVR_DPF((PVR_DBG_MESSAGE, "SGXInit: SGXMKIF structure sizes match. [ OK ]"));
        }
 
-       
+       /*
+        * Check ukernel build options against KM host driver
+        */
+
        ui32BuildOptions = psSGXFeatures->ui32BuildOptions;
        if (ui32BuildOptions != (SGX_BUILD_OPTIONS))
        {
@@ -2087,7 +2658,7 @@ PVRSRV_ERROR SGXDevInitCompatCheck(PVRSRV_DEVICE_NODE *psDeviceNode)
        {
                PVR_DPF((PVR_DBG_MESSAGE, "SGXInit: Driver and microkernel build options match. [ OK ]"));
        }
-#endif 
+#endif // NO_HARDWARE
 
        eError = PVRSRV_OK;
 chk_exit:
@@ -2098,16 +2669,27 @@ chk_exit:
 #endif
 }
 
+/*
+ * @Function   SGXGetMiscInfoUkernel
+ *
+ * @Description        Returns misc info (e.g. SGX build info/flags) from microkernel
+ *
+ * @Input      psDevInfo : device info from init phase
+ * @Input      psDeviceNode : device node, used for scheduling ukernel to query SGX features
+ *
+ * @Return     PVRSRV_ERROR :
+ *
+ */
 static
 PVRSRV_ERROR SGXGetMiscInfoUkernel(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                                                   PVRSRV_DEVICE_NODE   *psDeviceNode,
                                                                   IMG_HANDLE hDevMemContext)
 {
        PVRSRV_ERROR            eError;
-       SGXMKIF_COMMAND         sCommandData;  
-       PVRSRV_SGX_MISCINFO_INFO                        *psSGXMiscInfoInt;      
-       PVRSRV_SGX_MISCINFO_FEATURES            *psSGXFeatures;         
-       SGX_MISCINFO_STRUCT_SIZES                       *psSGXStructSizes;      
+       SGXMKIF_COMMAND         sCommandData;  /* CCB command data */
+       PVRSRV_SGX_MISCINFO_INFO                        *psSGXMiscInfoInt;      /*!< internal misc info for ukernel */
+       PVRSRV_SGX_MISCINFO_FEATURES            *psSGXFeatures;         /*!< sgx features for client */
+       SGX_MISCINFO_STRUCT_SIZES                       *psSGXStructSizes;      /*!< internal info: microkernel structure sizes */
 
        PPVRSRV_KERNEL_MEM_INFO psMemInfo = psDevInfo->psKernelSGXMiscMemInfo;
 
@@ -2122,12 +2704,12 @@ PVRSRV_ERROR SGXGetMiscInfoUkernel(PVRSRV_SGXDEV_INFO   *psDevInfo,
 
        psSGXMiscInfoInt->ui32MiscInfoFlags &= ~PVRSRV_USSE_MISCINFO_READY;
 
-       
+       /* Reset SGX features */
        OSMemSet(psSGXFeatures, 0, sizeof(*psSGXFeatures));
        OSMemSet(psSGXStructSizes, 0, sizeof(*psSGXStructSizes));
 
-       
-       sCommandData.ui32Data[1] = psMemInfo->sDevVAddr.uiAddr; 
+       /* set up buffer address for SGX features in CCB */
+       sCommandData.ui32Data[1] = psMemInfo->sDevVAddr.uiAddr; /* device V addr of output buffer */
 
        PDUMPCOMMENT("Microkernel kick for SGXGetMiscInfo");
        eError = SGXScheduleCCBCommandKM(psDeviceNode,
@@ -2144,7 +2726,9 @@ PVRSRV_ERROR SGXGetMiscInfoUkernel(PVRSRV_SGXDEV_INFO     *psDevInfo,
                return eError;
        }
 
-       
+       /* FIXME: DWORD value to determine code path in ukernel?
+        * E.g. could use getMiscInfo to obtain register values for diagnostics? */
+
 #if !defined(NO_HARDWARE)
        {
                IMG_BOOL bExit;
@@ -2159,20 +2743,33 @@ PVRSRV_ERROR SGXGetMiscInfoUkernel(PVRSRV_SGXDEV_INFO   *psDevInfo,
                        }
                } END_LOOP_UNTIL_TIMEOUT();
 
-               
+               /*if the loop exited because a timeout*/
                if (!bExit)
                {
                        PVR_DPF((PVR_DBG_ERROR, "SGXGetMiscInfoUkernel: Timeout occurred waiting for misc info."));
                        return PVRSRV_ERROR_TIMEOUT;
                }
        }
-#endif 
+#endif /* NO_HARDWARE */
 
        return PVRSRV_OK;
 }
 
 
 
+/*
+ * @Function   SGXGetMiscInfoKM
+ *
+ * @Description        Returns miscellaneous SGX info
+ *
+ * @Input      psDevInfo : device info from init phase
+ * @Input      psDeviceNode : device node, used for scheduling ukernel to query SGX features
+ *
+ * @Output     psMiscInfo : query request plus user-mode mem for holding returned data
+ *
+ * @Return     PVRSRV_ERROR :
+ *
+ */
 IMG_EXPORT
 PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO       *psDevInfo,
                                                          SGX_MISC_INFO                 *psMiscInfo,
@@ -2183,7 +2780,7 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
        PPVRSRV_KERNEL_MEM_INFO psMemInfo = psDevInfo->psKernelSGXMiscMemInfo;
        IMG_UINT32      *pui32MiscInfoFlags = &((PVRSRV_SGX_MISCINFO_INFO*)(psMemInfo->pvLinAddrKM))->ui32MiscInfoFlags;
 
-       
+       /* Reset the misc info state flags */
        *pui32MiscInfoFlags = 0;
 
 #if !defined(SUPPORT_SGX_EDM_MEMORY_DEBUG)
@@ -2204,14 +2801,14 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                        IMG_UINT32              ui32EndRegVal;
                        SGXMKIF_COMMAND sCommandData;
 
-                       
+                       /* Set or Clear BP? */
                        if(psMiscInfo->uData.sSGXBreakpointInfo.bBPEnable)
                        {
-                               
+                               /* set the break point */
                                IMG_DEV_VIRTADDR sBPDevVAddr = psMiscInfo->uData.sSGXBreakpointInfo.sBPDevVAddr;
                                IMG_DEV_VIRTADDR sBPDevVAddrEnd = psMiscInfo->uData.sSGXBreakpointInfo.sBPDevVAddrEnd;
 
-                               
+                               /* BP address */
                                ui32StartRegVal = sBPDevVAddr.uiAddr & EUR_CR_BREAKPOINT0_START_ADDRESS_MASK;
                                ui32EndRegVal = sBPDevVAddrEnd.uiAddr & EUR_CR_BREAKPOINT0_END_ADDRESS_MASK;
 
@@ -2220,7 +2817,7 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                ui32CtrlREnable = psMiscInfo->uData.sSGXBreakpointInfo.bRead;
                                ui32CtrlTrapEnable = psMiscInfo->uData.sSGXBreakpointInfo.bTrapped;
 
-                               
+                               /* normal data BP */
                                ui32RegVal = ((ui32MaskDM<<EUR_CR_BREAKPOINT0_MASK_DM_SHIFT) & EUR_CR_BREAKPOINT0_MASK_DM_MASK) |
                                                         ((ui32CtrlWEnable<<EUR_CR_BREAKPOINT0_CTRL_WENABLE_SHIFT) & EUR_CR_BREAKPOINT0_CTRL_WENABLE_MASK) |
                                                         ((ui32CtrlREnable<<EUR_CR_BREAKPOINT0_CTRL_RENABLE_SHIFT) & EUR_CR_BREAKPOINT0_CTRL_RENABLE_MASK) |
@@ -2228,17 +2825,17 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                        }
                        else
                        {
-                               
+                               /* clear the break point */
                                ui32RegVal = ui32StartRegVal = ui32EndRegVal = 0;
                        }
 
-                       
+                       /* setup the command */
                        sCommandData.ui32Data[0] = psMiscInfo->uData.sSGXBreakpointInfo.ui32BPIndex;
                        sCommandData.ui32Data[1] = ui32StartRegVal;
                        sCommandData.ui32Data[2] = ui32EndRegVal;
                        sCommandData.ui32Data[3] = ui32RegVal;
 
-                       
+                       /* clear signal flags */
                        psDevInfo->psSGXHostCtl->ui32BPSetClearSignal = 0;
 
                        PDUMPCOMMENT("Microkernel kick for setting a data breakpoint");
@@ -2257,7 +2854,7 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                        }
 
 #if defined(NO_HARDWARE)
-                       
+                       /* clear signal flags */
                        psDevInfo->psSGXHostCtl->ui32BPSetClearSignal = 0;
 #else
                        {
@@ -2269,43 +2866,46 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                        if (psDevInfo->psSGXHostCtl->ui32BPSetClearSignal != 0)
                                        {
                                                bExit = IMG_TRUE;
-                                               
+                                               /* clear signal flags */
                                                psDevInfo->psSGXHostCtl->ui32BPSetClearSignal = 0;
                                                break;
                                        }
                                } END_LOOP_UNTIL_TIMEOUT();
 
-                               
+                               /*if the loop exited because a timeout*/
                                if (!bExit)
                                {
                                        PVR_DPF((PVR_DBG_ERROR, "SGXGetMiscInfoKM: Timeout occurred waiting BP set/clear"));
                                        return PVRSRV_ERROR_TIMEOUT;
                                }
                        }
-#endif 
+#endif /* NO_HARDWARE */
 
                        return PVRSRV_OK;
                }
 
                case SGX_MISC_INFO_REQUEST_POLL_BREAKPOINT:
                {
-                       
-
-
-
-
-                       
-
+                       /* This request checks to see whether a breakpoint has
+                          been trapped.  If so, it returns the number of the
+                          breakpoint number that was trapped in ui32BPIndex,
+                          sTrappedBPDevVAddr to the address which was trapped,
+                          and sets bTrappedBP.  Otherwise, bTrappedBP will be
+                          false, and other fields should be ignored. */
+                       /* The uKernel is not used, since if we are stopped on a
+                          breakpoint, it is not possible to guarantee that the
+                          uKernel would be able to run */
 #if !defined(NO_HARDWARE)
 #if defined(SGX_FEATURE_MP)
                        IMG_BOOL bTrappedBPMaster;
                        IMG_UINT32 ui32CoreNum, ui32TrappedBPCoreNum;
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
                        IMG_UINT32 ui32PipeNum, ui32TrappedBPPipeNum;
+/* ui32PipeNum is the pipe number plus 1, or 0 to represent "partition" */
 #define NUM_PIPES_PLUS_ONE (SGX_FEATURE_PERPIPE_BKPT_REGS_NUMPIPES+1)
 #endif
                        IMG_BOOL bTrappedBPAny;
-#endif 
+#endif /* defined(SGX_FEATURE_MP) */
                        IMG_BOOL bFoundOne;
 
 #if defined(SGX_FEATURE_MP)
@@ -2313,14 +2913,15 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                        bTrappedBPMaster = !!(EUR_CR_MASTER_BREAKPOINT_TRAPPED_MASK & OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_BREAKPOINT));
                        bTrappedBPAny = bTrappedBPMaster;
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
-                       ui32TrappedBPPipeNum = 0; 
+                       ui32TrappedBPPipeNum = 0; /* just to keep the (incorrect) compiler happy */
 #endif
                        for (ui32CoreNum = 0; ui32CoreNum < SGX_FEATURE_MP_CORE_COUNT_3D; ui32CoreNum++)
                        {
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
-                               
-
-
+                               /* FIXME:  this macro makes the assumption that the PARTITION regs are the same
+                                  distance before the PIPE0 regs as the PIPE1 regs are after it, _and_
+                                  assumes that the fields in the partition regs are in the same place
+                                  in the pipe regs.  Need to validate these assumptions, or assert them */
 #define SGX_MP_CORE_PIPE_SELECT(r,c,p) \
                                ((SGX_MP_CORE_SELECT(EUR_CR_PARTITION_##r,c) + p*(EUR_CR_PIPE0_##r-EUR_CR_PARTITION_##r)))
                                for (ui32PipeNum = 0; ui32PipeNum < NUM_PIPES_PLUS_ONE; ui32PipeNum++)
@@ -2338,23 +2939,23 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                                ui32TrappedBPPipeNum = ui32PipeNum;
                                        }
                                }
-#else 
+#else /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
                                bFoundOne = !!(EUR_CR_BREAKPOINT_TRAPPED_MASK & OSReadHWReg(psDevInfo->pvRegsBaseKM, SGX_MP_CORE_SELECT(EUR_CR_BREAKPOINT, ui32CoreNum)));
                                if (bFoundOne)
                                {
                                        bTrappedBPAny = IMG_TRUE;
                                        ui32TrappedBPCoreNum = ui32CoreNum;
                                }
-#endif 
+#endif /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
                        }
 
                        psMiscInfo->uData.sSGXBreakpointInfo.bTrappedBP = bTrappedBPAny;
-#else 
+#else /* defined(SGX_FEATURE_MP) */
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
                        #error Not yet considered the case for per-pipe regs in non-mp case
 #endif
                        psMiscInfo->uData.sSGXBreakpointInfo.bTrappedBP = 0 != (EUR_CR_BREAKPOINT_TRAPPED_MASK & OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BREAKPOINT));
-#endif 
+#endif /* defined(SGX_FEATURE_MP) */
 
                        if (psMiscInfo->uData.sSGXBreakpointInfo.bTrappedBP)
                        {
@@ -2364,14 +2965,14 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
                                ui32Info0 = OSReadHWReg(psDevInfo->pvRegsBaseKM, bTrappedBPMaster?EUR_CR_MASTER_BREAKPOINT_TRAP_INFO0:SGX_MP_CORE_PIPE_SELECT(BREAKPOINT_TRAP_INFO0, ui32TrappedBPCoreNum, ui32TrappedBPPipeNum));
                                ui32Info1 = OSReadHWReg(psDevInfo->pvRegsBaseKM, bTrappedBPMaster?EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1:SGX_MP_CORE_PIPE_SELECT(BREAKPOINT_TRAP_INFO1, ui32TrappedBPCoreNum, ui32TrappedBPPipeNum));
-#else 
+#else /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
                                ui32Info0 = OSReadHWReg(psDevInfo->pvRegsBaseKM, bTrappedBPMaster?EUR_CR_MASTER_BREAKPOINT_TRAP_INFO0:SGX_MP_CORE_SELECT(EUR_CR_BREAKPOINT_TRAP_INFO0, ui32TrappedBPCoreNum));
                                ui32Info1 = OSReadHWReg(psDevInfo->pvRegsBaseKM, bTrappedBPMaster?EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1:SGX_MP_CORE_SELECT(EUR_CR_BREAKPOINT_TRAP_INFO1, ui32TrappedBPCoreNum));
-#endif 
-#else 
+#endif /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
+#else /* defined(SGX_FEATURE_MP) */
                                ui32Info0 = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BREAKPOINT_TRAP_INFO0);
                                ui32Info1 = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BREAKPOINT_TRAP_INFO1);
-#endif 
+#endif /* defined(SGX_FEATURE_MP) */
 
 #ifdef SGX_FEATURE_PERPIPE_BKPT_REGS
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32BPIndex = (ui32Info1 & EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_NUMBER_MASK) >> EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_NUMBER_SHIFT;
@@ -2380,41 +2981,41 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                psMiscInfo->uData.sSGXBreakpointInfo.bTrappedBPRead = !!(ui32Info1 & EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_RNW_MASK);
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32TrappedBPDataMaster = (ui32Info1 & EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_DATA_MASTER_MASK) >> EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_DATA_MASTER_SHIFT;
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32TrappedBPTag = (ui32Info1 & EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_TAG_MASK) >> EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_TAG_SHIFT;
-#else 
+#else /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32BPIndex = (ui32Info1 & EUR_CR_BREAKPOINT_TRAP_INFO1_NUMBER_MASK) >> EUR_CR_BREAKPOINT_TRAP_INFO1_NUMBER_SHIFT;
                                psMiscInfo->uData.sSGXBreakpointInfo.sTrappedBPDevVAddr.uiAddr = ui32Info0 & EUR_CR_BREAKPOINT_TRAP_INFO0_ADDRESS_MASK;
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32TrappedBPBurstLength = (ui32Info1 & EUR_CR_BREAKPOINT_TRAP_INFO1_SIZE_MASK) >> EUR_CR_BREAKPOINT_TRAP_INFO1_SIZE_SHIFT;
                                psMiscInfo->uData.sSGXBreakpointInfo.bTrappedBPRead = !!(ui32Info1 & EUR_CR_BREAKPOINT_TRAP_INFO1_RNW_MASK);
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32TrappedBPDataMaster = (ui32Info1 & EUR_CR_BREAKPOINT_TRAP_INFO1_DATA_MASTER_MASK) >> EUR_CR_BREAKPOINT_TRAP_INFO1_DATA_MASTER_SHIFT;
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32TrappedBPTag = (ui32Info1 & EUR_CR_BREAKPOINT_TRAP_INFO1_TAG_MASK) >> EUR_CR_BREAKPOINT_TRAP_INFO1_TAG_SHIFT;
-#endif 
+#endif /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
 #if defined(SGX_FEATURE_MP)
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
-                               
+                               /* mp, per-pipe regbanks */
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32CoreNum = bTrappedBPMaster?65535:(ui32TrappedBPCoreNum + (ui32TrappedBPPipeNum<<10));
-#else 
-                               
+#else /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
+                               /* mp, regbanks unsplit */
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32CoreNum = bTrappedBPMaster?65535:ui32TrappedBPCoreNum;
-#endif 
-#else 
+#endif /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
+#else /* defined(SGX_FEATURE_MP) */
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
-                               
+                               /* non-mp, per-pipe regbanks */
 #error non-mp perpipe regs not yet supported
-#else 
-                               
+#else /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
+                               /* non-mp */
                                psMiscInfo->uData.sSGXBreakpointInfo.ui32CoreNum = 65534;
-#endif 
-#endif 
+#endif /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
+#endif /* defined(SGX_FEATURE_MP) */
                        }
-#endif 
+#endif /* !defined(NO_HARDWARE) */
                        return PVRSRV_OK;
                }
 
                case SGX_MISC_INFO_REQUEST_RESUME_BREAKPOINT:
                {
-                       
-                       
-                       
+                       /* This request resumes from the currently trapped breakpoint. */
+                       /* Core number must be supplied */
+                       /* Polls for notify to be acknowledged by h/w */
 #if !defined(NO_HARDWARE)
 #if defined(SGX_FEATURE_MP)
                        IMG_UINT32 ui32CoreNum;
@@ -2422,7 +3023,7 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
                        IMG_UINT32 ui32PipeNum;
 #endif
-#endif 
+#endif /* defined(SGX_FEATURE_MP) */
                        IMG_UINT32 ui32OldSeqNum, ui32NewSeqNum;
 
 #if defined(SGX_FEATURE_MP)
@@ -2430,14 +3031,14 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                        ui32PipeNum = psMiscInfo->uData.sSGXBreakpointInfo.ui32CoreNum >> 10;
                        ui32CoreNum = psMiscInfo->uData.sSGXBreakpointInfo.ui32CoreNum & 1023;
                        bMaster = psMiscInfo->uData.sSGXBreakpointInfo.ui32CoreNum > 32767;
-#else 
+#else /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
                        ui32CoreNum = psMiscInfo->uData.sSGXBreakpointInfo.ui32CoreNum;
                        bMaster = ui32CoreNum > SGX_FEATURE_MP_CORE_COUNT_3D;
-#endif 
+#endif /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
                        if (bMaster)
                        {
-                               
-                               
+                               /* master */
+                               /* EUR_CR_MASTER_BREAKPOINT_TRAPPED_MASK | EUR_CR_MASTER_BREAKPOINT_SEQNUM_MASK */
                                ui32OldSeqNum = 0x1c & OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_BREAKPOINT);
                                OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_BREAKPOINT_TRAP, EUR_CR_MASTER_BREAKPOINT_TRAP_WRNOTIFY_MASK | EUR_CR_MASTER_BREAKPOINT_TRAP_CONTINUE_MASK);
                                do
@@ -2447,9 +3048,9 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                while (ui32OldSeqNum == ui32NewSeqNum);
                        }
                        else
-#endif 
+#endif /* defined(SGX_FEATURE_MP) */
                        {
-                               
+                               /* core */
 #if defined(SGX_FEATURE_PERPIPE_BKPT_REGS)
                                ui32OldSeqNum = 0x1c & OSReadHWReg(psDevInfo->pvRegsBaseKM, SGX_MP_CORE_PIPE_SELECT(BREAKPOINT, ui32CoreNum, ui32PipeNum));
                                OSWriteHWReg(psDevInfo->pvRegsBaseKM, SGX_MP_CORE_PIPE_SELECT(BREAKPOINT_TRAP, ui32CoreNum, ui32PipeNum), EUR_CR_PARTITION_BREAKPOINT_TRAP_WRNOTIFY_MASK | EUR_CR_PARTITION_BREAKPOINT_TRAP_CONTINUE_MASK);
@@ -2458,7 +3059,7 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                        ui32NewSeqNum = 0x1c & OSReadHWReg(psDevInfo->pvRegsBaseKM, SGX_MP_CORE_PIPE_SELECT(BREAKPOINT, ui32CoreNum, ui32PipeNum));
                                }
                                while (ui32OldSeqNum == ui32NewSeqNum);
-#else 
+#else /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
                                ui32OldSeqNum = 0x1c & OSReadHWReg(psDevInfo->pvRegsBaseKM, SGX_MP_CORE_SELECT(EUR_CR_BREAKPOINT, ui32CoreNum));
                                OSWriteHWReg(psDevInfo->pvRegsBaseKM, SGX_MP_CORE_SELECT(EUR_CR_BREAKPOINT_TRAP, ui32CoreNum), EUR_CR_BREAKPOINT_TRAP_WRNOTIFY_MASK | EUR_CR_BREAKPOINT_TRAP_CONTINUE_MASK);
                                do
@@ -2466,12 +3067,12 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                        ui32NewSeqNum = 0x1c & OSReadHWReg(psDevInfo->pvRegsBaseKM, SGX_MP_CORE_SELECT(EUR_CR_BREAKPOINT, ui32CoreNum));
                                }
                                while (ui32OldSeqNum == ui32NewSeqNum);
-#endif 
+#endif /* defined(SGX_FEATURE_PERPIPE_BKPT_REGS) */
                        }
-#endif 
+#endif /* !defined(NO_HARDWARE) */
                        return PVRSRV_OK;
                }
-#endif 
+#endif /* SGX_FEATURE_DATA_BREAKPOINTS)        */
 
                case SGX_MISC_INFO_REQUEST_CLOCKSPEED:
                {
@@ -2499,13 +3100,15 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
 
                case SGX_MISC_INFO_REQUEST_SPM:
                {
-                       
+                       /* this is dealt with in UM */
                        return PVRSRV_OK;
                }
 
                case SGX_MISC_INFO_REQUEST_SGXREV:
                {
                        PVRSRV_SGX_MISCINFO_FEATURES            *psSGXFeatures;
+//                     PPVRSRV_KERNEL_MEM_INFO psMemInfo = psDevInfo->psKernelSGXMiscMemInfo;
+
                        eError = SGXGetMiscInfoUkernel(psDevInfo, psDeviceNode, hDevMemContext);
                        if(eError != PVRSRV_OK)
                        {
@@ -2515,10 +3118,10 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                        }
                        psSGXFeatures = &((PVRSRV_SGX_MISCINFO_INFO*)(psMemInfo->pvLinAddrKM))->sSGXFeatures;
 
-                       
+                       /* Copy SGX features into misc info struct, to return to client */
                        psMiscInfo->uData.sSGXFeatures = *psSGXFeatures;
 
-                       
+                       /* Debug output */
                        PVR_DPF((PVR_DBG_MESSAGE, "SGXGetMiscInfoKM: Core 0x%x, sw ID 0x%x, sw Rev 0x%x\n",
                                        psSGXFeatures->ui32CoreRev,
                                        psSGXFeatures->ui32CoreIdSW,
@@ -2527,7 +3130,7 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                        psSGXFeatures->ui32DDKVersion,
                                        psSGXFeatures->ui32DDKBuild));
 
-                       
+                       /* done! */
                        return PVRSRV_OK;
                }
 
@@ -2537,7 +3140,9 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
 
                        psSGXFeatures = &((PVRSRV_SGX_MISCINFO_INFO*)(psMemInfo->pvLinAddrKM))->sSGXFeatures;
 
-                       
+                       /* Reset the misc information to prevent
+                        * confusion with values returned from the ukernel
+                        */
                        OSMemSet(psMemInfo->pvLinAddrKM, 0,
                                        sizeof(PVRSRV_SGX_MISCINFO_INFO));
 
@@ -2547,16 +3152,16 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                PVRVERSION_BRANCH;
                        psSGXFeatures->ui32DDKBuild = PVRVERSION_BUILD;
 
-                       
+                       /* Also report the kernel module build options -- used in SGXConnectionCheck() */
                        psSGXFeatures->ui32BuildOptions = (SGX_BUILD_OPTIONS);
 
 #if defined(PVRSRV_USSE_EDM_STATUS_DEBUG)
-                       
+                       /* Report the EDM status buffer location in memory */
                        psSGXFeatures->sDevVAEDMStatusBuffer = psDevInfo->psKernelEDMStatusBufferMemInfo->sDevVAddr;
                        psSGXFeatures->pvEDMStatusBuffer = psDevInfo->psKernelEDMStatusBufferMemInfo->pvLinAddrKM;
 #endif
 
-                       
+                       /* Copy SGX features into misc info struct, to return to client */
                        psMiscInfo->uData.sSGXFeatures = *psSGXFeatures;
                        return PVRSRV_OK;
                }
@@ -2567,17 +3172,17 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                {
                        PVRSRV_ERROR eError;
                        PVRSRV_SGX_MISCINFO_FEATURES            *psSGXFeatures;
-                       PVRSRV_SGX_MISCINFO_MEMACCESS           *psSGXMemSrc;   
-                       PVRSRV_SGX_MISCINFO_MEMACCESS           *psSGXMemDest;  
+                       PVRSRV_SGX_MISCINFO_MEMACCESS           *psSGXMemSrc;   /* user-defined mem read */
+                       PVRSRV_SGX_MISCINFO_MEMACCESS           *psSGXMemDest;  /* user-defined mem write */
 
                        {                               
-                               
+                               /* Set the mem read flag; src is user-defined */
                                *pui32MiscInfoFlags |= PVRSRV_USSE_MISCINFO_MEMREAD;
                                psSGXMemSrc = &((PVRSRV_SGX_MISCINFO_INFO*)(psMemInfo->pvLinAddrKM))->sSGXMemAccessSrc;
 
                                if(psMiscInfo->sDevVAddrSrc.uiAddr != 0)
                                {
-                                       psSGXMemSrc->sDevVAddr = psMiscInfo->sDevVAddrSrc; 
+                                       psSGXMemSrc->sDevVAddr = psMiscInfo->sDevVAddrSrc; /* src address */
                                }
                                else
                                {
@@ -2587,13 +3192,13 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
 
                        if( psMiscInfo->eRequest == SGX_MISC_INFO_REQUEST_MEMCOPY)
                        {                               
-                               
+                               /* Set the mem write flag; dest is user-defined */
                                *pui32MiscInfoFlags |= PVRSRV_USSE_MISCINFO_MEMWRITE;
                                psSGXMemDest = &((PVRSRV_SGX_MISCINFO_INFO*)(psMemInfo->pvLinAddrKM))->sSGXMemAccessDest;
                                
                                if(psMiscInfo->sDevVAddrDest.uiAddr != 0)
                                {
-                                       psSGXMemDest->sDevVAddr = psMiscInfo->sDevVAddrDest; 
+                                       psSGXMemDest->sDevVAddr = psMiscInfo->sDevVAddrDest; /* dest address */
                                }
                                else
                                {
@@ -2601,12 +3206,12 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                }
                        }
 
-                       
+                       /* Get physical address of PD for memory read (may need to switch context in microkernel) */
                        if(psMiscInfo->hDevMemContext != IMG_NULL)
                        {
                                SGXGetMMUPDAddrKM( (IMG_HANDLE)psDeviceNode, hDevMemContext, &psSGXMemSrc->sPDDevPAddr);
                                
-                               
+                               /* Single app will always use the same src and dest mem context */
                                psSGXMemDest->sPDDevPAddr = psSGXMemSrc->sPDDevPAddr;
                        }
                        else
@@ -2614,7 +3219,7 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                return PVRSRV_ERROR_INVALID_PARAMS;
                        }
 
-                       
+                       /* Submit the task to the ukernel */
                        eError = SGXGetMiscInfoUkernel(psDevInfo, psDeviceNode);
                        if(eError != PVRSRV_OK)
                        {
@@ -2630,11 +3235,11 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                return PVRSRV_ERROR_INVALID_MISCINFO;
                        }
 #endif
-                       
+                       /* Copy SGX features into misc info struct, to return to client */
                        psMiscInfo->uData.sSGXFeatures = *psSGXFeatures;
                        return PVRSRV_OK;
                }
-#endif 
+#endif /* SUPPORT_SGX_EDM_MEMORY_DEBUG */
 
 #if defined(SUPPORT_SGX_HWPERF)
                case SGX_MISC_INFO_REQUEST_SET_HWPERF_STATUS:
@@ -2646,7 +3251,7 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                                                                                 PVRSRV_SGX_HWPERF_STATUS_MK_EXECUTION_ON;
                        SGXMKIF_COMMAND         sCommandData = {0};
 
-                       
+                       /* Check for valid flags */
                        if ((psSetHWPerfStatus->ui32NewHWPerfStatus & ~ui32ValidFlags) != 0)
                        {
                                return PVRSRV_ERROR_INVALID_PARAMS;
@@ -2656,9 +3261,9 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS,
                                                                  "SGX ukernel HWPerf status %u\n",
                                                                  psSetHWPerfStatus->ui32NewHWPerfStatus);
-                       #endif 
+                       #endif /* PDUMP */
 
-                       
+                       /* Copy the new group selector(s) to the host ctl for the ukernel */
                        #if defined(SGX_FEATURE_EXTENDED_PERF_COUNTERS)
                        OSMemCopy(&psDevInfo->psSGXHostCtl->aui32PerfGroup[0],
                                          &psSetHWPerfStatus->aui32PerfGroup[0],
@@ -2666,6 +3271,8 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO  *psDevInfo,
                        OSMemCopy(&psDevInfo->psSGXHostCtl->aui32PerfBit[0],
                                          &psSetHWPerfStatus->aui32PerfBit[0],
                                          sizeof(psDevInfo->psSGXHostCtl->aui32PerfBit));
+                       psDevInfo->psSGXHostCtl->ui32PerfCounterBitSelect = psSetHWPerfStatus->ui32PerfCounterBitSelect;
+                       psDevInfo->psSGXHostCtl->ui32PerfSumMux = psSetHWPerfStatus->ui32PerfSumMux;
                        #if defined(PDUMP)
                        PDUMPMEM(IMG_NULL, psDevInfo->psKernelSGXHostCtlMemInfo,
                                         offsetof(SGXMKIF_HOST_CTL, aui32PerfGroup),
@@ -2677,7 +3284,17 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO *psDevInfo,
                                         sizeof(psDevInfo->psSGXHostCtl->aui32PerfBit),
                                         PDUMP_FLAGS_CONTINUOUS,
                                         MAKEUNIQUETAG(psDevInfo->psKernelSGXHostCtlMemInfo));
-                       #endif 
+                       PDUMPMEM(IMG_NULL, psDevInfo->psKernelSGXHostCtlMemInfo,
+                                        offsetof(SGXMKIF_HOST_CTL, ui32PerfCounterBitSelect),
+                                        sizeof(psDevInfo->psSGXHostCtl->ui32PerfCounterBitSelect),
+                                        PDUMP_FLAGS_CONTINUOUS,
+                                        MAKEUNIQUETAG(psDevInfo->psKernelSGXHostCtlMemInfo));
+                       PDUMPMEM(IMG_NULL, psDevInfo->psKernelSGXHostCtlMemInfo,
+                                        offsetof(SGXMKIF_HOST_CTL, ui32PerfSumMux),
+                                        sizeof(psDevInfo->psSGXHostCtl->ui32PerfSumMux),
+                                        PDUMP_FLAGS_CONTINUOUS,
+                                        MAKEUNIQUETAG(psDevInfo->psKernelSGXHostCtlMemInfo));
+                       #endif /* PDUMP */
                        #else
                        psDevInfo->psSGXHostCtl->ui32PerfGroup = psSetHWPerfStatus->ui32PerfGroup;
                        #if defined(PDUMP)
@@ -2686,10 +3303,10 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                         sizeof(psDevInfo->psSGXHostCtl->ui32PerfGroup),
                                         PDUMP_FLAGS_CONTINUOUS,
                                         MAKEUNIQUETAG(psDevInfo->psKernelSGXHostCtlMemInfo));
-                       #endif 
-                       #endif 
+                       #endif /* PDUMP */
+                       #endif /* SGX_FEATURE_EXTENDED_PERF_COUNTERS */
 
-                       
+                       /* Kick the ukernel to update the hardware state */
                        sCommandData.ui32Data[0] = psSetHWPerfStatus->ui32NewHWPerfStatus;
                        eError = SGXScheduleCCBCommandKM(psDeviceNode,
                                                                                         SGXMKIF_CMD_SETHWPERFSTATUS,
@@ -2700,18 +3317,30 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                                                                         IMG_FALSE);
                        return eError;
                }
-#endif 
+#endif /* SUPPORT_SGX_HWPERF */
 
                case SGX_MISC_INFO_DUMP_DEBUG_INFO:
                {
                        PVR_LOG(("User requested SGX debug info"));
 
-                       
+                       /* Dump SGX debug data to the kernel log. */
                        SGXDumpDebugInfo(psDeviceNode->pvDevice, IMG_FALSE);
 
                        return PVRSRV_OK;
                }
 
+               case SGX_MISC_INFO_DUMP_DEBUG_INFO_FORCE_REGS:
+               {
+                       PVR_LOG(("User requested SGX debug info"));
+
+                       /* Dump SGX debug data to the kernel log. */
+                       SGXDumpDebugInfo(psDeviceNode->pvDevice, IMG_TRUE);
+
+                       return PVRSRV_OK;
+               }
+
+#if defined(DEBUG)
+               /* Don't allow user-mode to reboot the device in production drivers */
                case SGX_MISC_INFO_PANIC:
                {
                        PVR_LOG(("User requested SGX panic"));
@@ -2720,10 +3349,11 @@ PVRSRV_ERROR SGXGetMiscInfoKM(PVRSRV_SGXDEV_INFO        *psDevInfo,
 
                        return PVRSRV_OK;
                }
+#endif
 
                default:
                {
-                       
+                       /* switch statement fell though, so: */
                        return PVRSRV_ERROR_INVALID_PARAMS;
                }
        }
@@ -2778,3 +3408,6 @@ PVRSRV_ERROR SGXReadHWPerfCBKM(IMG_HANDLE                                 hDevHandle,
 }
 
 
+/******************************************************************************
+ End of file (sgxinit.c)
+******************************************************************************/
index d1220cf..a0f6fa9 100644 (file)
@@ -1,30 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
-#include <stddef.h> 
+/*************************************************************************/ /*!
+@Title          Device specific kickTA routines
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+#include <stddef.h> /* For the macro offsetof() */
 #include "services_headers.h"
 #include "sgxinfo.h"
 #include "sgxinfokm.h"
 #include "sgxutils.h"
 #include "ttrace.h"
 
+/*!
+******************************************************************************
+
+ @Function     SGXDoKickKM
+
+ @Description
+
+ Really kicks the TA
+
+ @Input hDevHandle - Device handle
+
+ @Return ui32Error - success or failure
+
+******************************************************************************/
 IMG_EXPORT
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK_KM *psCCBKick)
@@ -62,15 +91,31 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                PVR_TTRACE(PVRSRV_TRACE_GROUP_KICK, PVRSRV_TRACE_CLASS_FUNCTION_EXIT, KICK_TOKEN_DOKICK);
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
-       
-       
+       /* override QAC warning about stricter alignment */
+       /* PRQA S 3305 1 */
        psTACmd = CCB_DATA_FROM_OFFSET(SGXMKIF_CMDTA_SHARED, psCCBMemInfo, psCCBKick, ui32CCBOffset);
 
        PVR_TTRACE(PVRSRV_TRACE_GROUP_KICK, PVRSRV_TRACE_CLASS_CMD_START, KICK_TOKEN_DOKICK);
+
+#if defined(TTRACE)
+       if (psCCBKick->bFirstKickOrResume)
+       {
+               PVR_TTRACE(PVRSRV_TRACE_GROUP_KICK,
+                                  PVRSRV_TRACE_CLASS_FLAGS,
+                                  KICK_TOKEN_FIRST_KICK);
+       }
+
+       if (psCCBKick->bLastInScene)
+       {
+               PVR_TTRACE(PVRSRV_TRACE_GROUP_KICK,
+                                  PVRSRV_TRACE_CLASS_FLAGS,
+                                  KICK_TOKEN_LAST_KICK);
+       }
+#endif
        PVR_TTRACE_UI32(PVRSRV_TRACE_GROUP_KICK, PVRSRV_TRACE_CLASS_CCB,
                        KICK_TOKEN_CCB_OFFSET, psCCBKick->ui32CCBOffset);
 
-       
+       /* TA/3D dependency */
        if (psCCBKick->hTA3DSyncInfo)
        {
                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psCCBKick->hTA3DSyncInfo;
@@ -119,7 +164,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
        psTACmd->ui32NumTAStatusVals = psCCBKick->ui32NumTAStatusVals;
        if (psCCBKick->ui32NumTAStatusVals != 0)
        {
-               
+               /* Copy status vals over */
                for (i = 0; i < psCCBKick->ui32NumTAStatusVals; i++)
                {
 #if defined(SUPPORT_SGX_NEW_STATUS_VALS)
@@ -135,7 +180,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
        psTACmd->ui32Num3DStatusVals = psCCBKick->ui32Num3DStatusVals;
        if (psCCBKick->ui32Num3DStatusVals != 0)
        {
-               
+               /* Copy status vals over */
                for (i = 0; i < psCCBKick->ui32Num3DStatusVals; i++)
                {
 #if defined(SUPPORT_SGX_NEW_STATUS_VALS)
@@ -150,7 +195,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
 
 
 #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS)
-       
+       /* SRC and DST sync dependencies */
        psTACmd->ui32NumTASrcSyncs = psCCBKick->ui32NumTASrcSyncs;
        for (i=0; i<psCCBKick->ui32NumTASrcSyncs; i++)
        {
@@ -159,9 +204,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                psTACmd->asTASrcSyncs[i].sWriteOpsCompleteDevVAddr = psSyncInfo->sWriteOpsCompleteDevVAddr;
                psTACmd->asTASrcSyncs[i].sReadOpsCompleteDevVAddr = psSyncInfo->sReadOpsCompleteDevVAddr;
 
-               
+               /* Get ui32ReadOpsPending snapshot and copy into the CCB - before incrementing. */
                psTACmd->asTASrcSyncs[i].ui32ReadOpsPendingVal = psSyncInfo->psSyncData->ui32ReadOpsPending++;
-               
+               /* Copy ui32WriteOpsPending snapshot into the CCB. */
                psTACmd->asTASrcSyncs[i].ui32WriteOpsPendingVal = psSyncInfo->psSyncData->ui32WriteOpsPending;
        }
 
@@ -173,9 +218,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                psTACmd->asTADstSyncs[i].sWriteOpsCompleteDevVAddr = psSyncInfo->sWriteOpsCompleteDevVAddr;
                psTACmd->asTADstSyncs[i].sReadOpsCompleteDevVAddr = psSyncInfo->sReadOpsCompleteDevVAddr;
 
-               
+               /* Get ui32ReadOpsPending snapshot and copy into the CCB */
                psTACmd->asTADstSyncs[i].ui32ReadOpsPendingVal = psSyncInfo->psSyncData->ui32ReadOpsPending;
-               
+               /* Copy ui32WriteOpsPending snapshot into the CCB - before incrementing */
                psTACmd->asTADstSyncs[i].ui32WriteOpsPendingVal = psSyncInfo->psSyncData->ui32WriteOpsPending++;
        }
 
@@ -187,13 +232,13 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                psTACmd->as3DSrcSyncs[i].sWriteOpsCompleteDevVAddr = psSyncInfo->sWriteOpsCompleteDevVAddr;
                psTACmd->as3DSrcSyncs[i].sReadOpsCompleteDevVAddr = psSyncInfo->sReadOpsCompleteDevVAddr;
 
-               
+               /* Get ui32ReadOpsPending snapshot and copy into the CCB - before incrementing. */
                psTACmd->as3DSrcSyncs[i].ui32ReadOpsPendingVal = psSyncInfo->psSyncData->ui32ReadOpsPending++;
-               
+               /* Copy ui32WriteOpsPending snapshot into the CCB. */
                psTACmd->as3DSrcSyncs[i].ui32WriteOpsPendingVal = psSyncInfo->psSyncData->ui32WriteOpsPending;
        }
-#else 
-       
+#else /* SUPPORT_SGX_GENERALISED_SYNCOBJECTS */
+       /* texture dependencies */
        psTACmd->ui32NumSrcSyncs = psCCBKick->ui32NumSrcSyncs;
        for (i=0; i<psCCBKick->ui32NumSrcSyncs; i++)
        {
@@ -205,12 +250,12 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                psTACmd->asSrcSyncs[i].sWriteOpsCompleteDevVAddr = psSyncInfo->sWriteOpsCompleteDevVAddr;
                psTACmd->asSrcSyncs[i].sReadOpsCompleteDevVAddr = psSyncInfo->sReadOpsCompleteDevVAddr;
 
-               
+               /* Get ui32ReadOpsPending snapshot and copy into the CCB - before incrementing. */
                psTACmd->asSrcSyncs[i].ui32ReadOpsPendingVal = psSyncInfo->psSyncData->ui32ReadOpsPending++;
-               
+               /* Copy ui32WriteOpsPending snapshot into the CCB. */
                psTACmd->asSrcSyncs[i].ui32WriteOpsPendingVal = psSyncInfo->psSyncData->ui32WriteOpsPending;
        }
-#endif
+#endif/* SUPPORT_SGX_GENERALISED_SYNCOBJECTS */
 
        if (psCCBKick->bFirstKickOrResume && psCCBKick->ui32NumDstSyncObjects > 0)
        {
@@ -242,15 +287,18 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
 
                        if (psSyncInfo)
                        {
+                               psSyncInfo->psSyncData->ui64LastWrite = ui64KickCount;
 
                                PVR_TTRACE_SYNC_OBJECT(PVRSRV_TRACE_GROUP_KICK, KICK_TOKEN_DST_SYNC,
                                                        psSyncInfo, PVRSRV_SYNCOP_SAMPLE);
 
                                psHWDeviceSyncList->asSyncData[i].sWriteOpsCompleteDevVAddr = psSyncInfo->sWriteOpsCompleteDevVAddr;
                                psHWDeviceSyncList->asSyncData[i].sReadOpsCompleteDevVAddr = psSyncInfo->sReadOpsCompleteDevVAddr;
+                               psHWDeviceSyncList->asSyncData[i].sReadOps2CompleteDevVAddr = psSyncInfo->sReadOps2CompleteDevVAddr;
 
                                psHWDeviceSyncList->asSyncData[i].ui32ReadOpsPendingVal = psSyncInfo->psSyncData->ui32ReadOpsPending;
                                psHWDeviceSyncList->asSyncData[i].ui32WriteOpsPendingVal = psSyncInfo->psSyncData->ui32WriteOpsPending++;
+                               psHWDeviceSyncList->asSyncData[i].ui32ReadOps2PendingVal = psSyncInfo->psSyncData->ui32ReadOps2Pending;
 
        #if defined(PDUMP)
                                if (PDumpIsCaptureFrameKM())
@@ -262,6 +310,8 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                                                                                + offsetof(PVRSRV_DEVICE_SYNC_OBJECT, ui32WriteOpsPendingVal);
                                        IMG_UINT32 ui32ROpsOffset = ui32SyncOffset
                                                                                                + offsetof(PVRSRV_DEVICE_SYNC_OBJECT, ui32ReadOpsPendingVal);
+                                       IMG_UINT32 ui32ROps2Offset = ui32SyncOffset
+                                                                                               + offsetof(PVRSRV_DEVICE_SYNC_OBJECT, ui32ReadOps2PendingVal);
 
                                        PDUMPCOMMENT("HWDeviceSyncObject for RT: %i\r\n", i);
 
@@ -275,7 +325,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                        if ((psSyncInfo->psSyncData->ui32LastOpDumpVal == 0) &&
                                                (psSyncInfo->psSyncData->ui32LastReadOpDumpVal == 0))
                                        {
-                                               
+                                               /*
+                                               * Init the ROpsComplete value to 0.
+                                               */
                                                PDUMPCOMMENT("Init RT ROpsComplete\r\n");
                                                PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                                        psSyncInfo->psSyncDataMemInfoKM,
@@ -283,7 +335,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                                        sizeof(psSyncInfo->psSyncData->ui32ReadOpsComplete),
                                                        0,
                                                        MAKEUNIQUETAG(psSyncInfo->psSyncDataMemInfoKM));
-                                               
+                                               /*
+                                               * Init the WOpsComplete value to 0.
+                                               */
                                                PDUMPCOMMENT("Init RT WOpsComplete\r\n");
                                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                                                psSyncInfo->psSyncDataMemInfoKM,
@@ -315,23 +369,37 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                                 sizeof(IMG_UINT32),
                                                 0,
                                                MAKEUNIQUETAG(psHWDstSyncListMemInfo));
+
+                                       /*
+                                       * Force the ROps2Complete value to 0.
+                                       */
+                                       PDUMPCOMMENT("Modify RT %d ROps2PendingVal in HWDevSyncList\r\n", i);
+                                       PDUMPMEM(&ui32ModifiedValue,
+                                               psHWDstSyncListMemInfo,
+                                               ui32ROps2Offset,
+                                               sizeof(IMG_UINT32),
+                                               0,
+                                               MAKEUNIQUETAG(psHWDstSyncListMemInfo));
                                }
-       #endif  
+       #endif  /* defined(PDUMP) */
                        }
                        else
                        {
                                psHWDeviceSyncList->asSyncData[i].sWriteOpsCompleteDevVAddr.uiAddr = 0;
                                psHWDeviceSyncList->asSyncData[i].sReadOpsCompleteDevVAddr.uiAddr = 0;
+                               psHWDeviceSyncList->asSyncData[i].sReadOps2CompleteDevVAddr.uiAddr = 0;
 
                                psHWDeviceSyncList->asSyncData[i].ui32ReadOpsPendingVal = 0;
+                               psHWDeviceSyncList->asSyncData[i].ui32ReadOps2PendingVal = 0;
                                psHWDeviceSyncList->asSyncData[i].ui32WriteOpsPendingVal = 0;
                        }
                }
        }
        
-       
-
-
+       /* 
+               NOTE: THIS MUST BE THE LAST THING WRITTEN TO THE TA COMMAND!
+               Set the ready for so the uKernel will process the command.
+       */
        psTACmd->ui32CtrlFlags |= SGXMKIF_CMDTA_CTRLFLAGS_READY;
 
 #if defined(PDUMP)
@@ -355,7 +423,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                        if ((psSyncInfo->psSyncData->ui32LastOpDumpVal == 0) &&
                                (psSyncInfo->psSyncData->ui32LastReadOpDumpVal == 0))
                        {
-                               
+                               /*
+                               * Init the ROpsComplete value to 0.
+                               */
                                PDUMPCOMMENT("Init RT TA-SRC ROpsComplete\r\n", i);
                                PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                        psSyncInfo->psSyncDataMemInfoKM,
@@ -363,7 +433,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                        sizeof(psSyncInfo->psSyncData->ui32ReadOpsComplete),
                                        0,
                                        MAKEUNIQUETAG(psSyncInfo->psSyncDataMemInfoKM));
-                               
+                               /*
+                               * Init the WOpsComplete value to 0.
+                               */
                                PDUMPCOMMENT("Init RT TA-SRC WOpsComplete\r\n");
                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                                psSyncInfo->psSyncDataMemInfoKM,
@@ -406,7 +478,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                        if ((psSyncInfo->psSyncData->ui32LastOpDumpVal == 0) &&
                                (psSyncInfo->psSyncData->ui32LastReadOpDumpVal == 0))
                        {
-                               
+                               /*
+                                * Init the ROpsComplete value to 0.
+                                */
                                PDUMPCOMMENT("Init RT TA-DST ROpsComplete\r\n", i);
                                PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                        psSyncInfo->psSyncDataMemInfoKM,
@@ -414,7 +488,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                        sizeof(psSyncInfo->psSyncData->ui32ReadOpsComplete),
                                        0,
                                        MAKEUNIQUETAG(psSyncInfo->psSyncDataMemInfoKM));
-                               
+                               /*
+                                * Init the WOpsComplete value to 0.
+                                */
                                PDUMPCOMMENT("Init RT TA-DST WOpsComplete\r\n");
                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                                psSyncInfo->psSyncDataMemInfoKM,
@@ -457,7 +533,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                        if ((psSyncInfo->psSyncData->ui32LastOpDumpVal == 0) &&
                                (psSyncInfo->psSyncData->ui32LastReadOpDumpVal == 0))
                        {
-                               
+                               /*
+                               * Init the ROpsComplete value to 0.
+                               */
                                PDUMPCOMMENT("Init RT 3D-SRC ROpsComplete\r\n", i);
                                PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                        psSyncInfo->psSyncDataMemInfoKM,
@@ -465,7 +543,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                        sizeof(psSyncInfo->psSyncData->ui32ReadOpsComplete),
                                        0,
                                        MAKEUNIQUETAG(psSyncInfo->psSyncDataMemInfoKM));
-                               
+                               /*
+                               * Init the WOpsComplete value to 0.
+                               */
                                PDUMPCOMMENT("Init RT 3D-SRC WOpsComplete\r\n");
                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                                psSyncInfo->psSyncDataMemInfoKM,
@@ -499,7 +579,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                0,
                                MAKEUNIQUETAG(psCCBMemInfo));
                }
-#else
+#else/* SUPPORT_SGX_GENERALISED_SYNCOBJECTS */
                for (i=0; i<psCCBKick->ui32NumSrcSyncs; i++)
                {
                        IMG_UINT32      ui32ModifiedValue;
@@ -508,7 +588,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                        if ((psSyncInfo->psSyncData->ui32LastOpDumpVal == 0) &&
                                (psSyncInfo->psSyncData->ui32LastReadOpDumpVal == 0))
                        {
-                               
+                               /*
+                               * Init the ROpsComplete value to 0.
+                               */
                                PDUMPCOMMENT("Init RT ROpsComplete\r\n");
                                PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                        psSyncInfo->psSyncDataMemInfoKM,
@@ -516,7 +598,9 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                        sizeof(psSyncInfo->psSyncData->ui32ReadOpsComplete),
                                        0,
                                        MAKEUNIQUETAG(psSyncInfo->psSyncDataMemInfoKM));
-                               
+                               /*
+                               * Init the WOpsComplete value to 0.
+                               */
                                PDUMPCOMMENT("Init RT WOpsComplete\r\n");
                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                                psSyncInfo->psSyncDataMemInfoKM,
@@ -524,6 +608,16 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                                                sizeof(psSyncInfo->psSyncData->ui32WriteOpsComplete),
                                                0,
                                                MAKEUNIQUETAG(psSyncInfo->psSyncDataMemInfoKM));
+                               /*
+                               * Init the ROps2Complete value to 0.
+                               */
+                               PDUMPCOMMENT("Init RT WOpsComplete\r\n");
+                                       PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
+                                               psSyncInfo->psSyncDataMemInfoKM,
+                                               offsetof(PVRSRV_SYNC_DATA, ui32ReadOps2Complete),
+                                               sizeof(psSyncInfo->psSyncData->ui32ReadOps2Complete),
+                                               0,
+                                               MAKEUNIQUETAG(psSyncInfo->psSyncDataMemInfoKM));
                        }
 
                        psSyncInfo->psSyncData->ui32LastReadOpDumpVal++;
@@ -581,7 +675,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                        psSyncInfo->psSyncData->ui32LastReadOpDumpVal++;
                }
 
-#endif
+#endif/* SUPPORT_SGX_GENERALISED_SYNCOBJECTS */
 
                for (i = 0; i < psCCBKick->ui32NumTAStatusVals; i++)
                {
@@ -611,7 +705,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
 #endif
                }
        }
-#endif 
+#endif /* defined(PDUMP) */
 
        PVR_TTRACE(PVRSRV_TRACE_GROUP_KICK, PVRSRV_TRACE_CLASS_CMD_END,
                        KICK_TOKEN_DOKICK);
@@ -623,7 +717,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                {
                        for (i=0; i < psCCBKick->ui32NumDstSyncObjects; i++)
                        {
-                               
+                               /* Client will retry, so undo the write ops pending increment done above. */
                                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psCCBKick->pahDstSyncHandles[i];
 
                                if (psSyncInfo)
@@ -655,13 +749,13 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                        psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *) psCCBKick->ah3DSrcKernelSyncInfo[i];
                        psSyncInfo->psSyncData->ui32ReadOpsPending--;
                }
-#else
+#else/* SUPPORT_SGX_GENERALISED_SYNCOBJECTS */
                for (i=0; i<psCCBKick->ui32NumSrcSyncs; i++)
                {
                        psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *) psCCBKick->ahSrcKernelSyncInfo[i];
                        psSyncInfo->psSyncData->ui32ReadOpsPending--;
                }
-#endif
+#endif/* SUPPORT_SGX_GENERALISED_SYNCOBJECTS */
 
                PVR_TTRACE(PVRSRV_TRACE_GROUP_KICK, PVRSRV_TRACE_CLASS_FUNCTION_EXIT,
                                KICK_TOKEN_DOKICK);
@@ -679,7 +773,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
 #if defined(NO_HARDWARE)
 
 
-       
+       /* TA/3D dependency */
        if (psCCBKick->hTA3DSyncInfo)
        {
                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psCCBKick->hTA3DSyncInfo;
@@ -704,12 +798,12 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                psSyncInfo->psSyncData->ui32ReadOpsComplete =  psSyncInfo->psSyncData->ui32ReadOpsPending;
        }
 
-       
+       /* Copy status vals over */
        for (i = 0; i < psCCBKick->ui32NumTAStatusVals; i++)
        {
 #if defined(SUPPORT_SGX_NEW_STATUS_VALS)
                PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo = (PVRSRV_KERNEL_MEM_INFO*)psCCBKick->asTAStatusUpdate[i].hKernelMemInfo;
-               
+               /* derive offset into meminfo and write the status value */
                *(IMG_UINT32*)((IMG_UINTPTR_T)psKernelMemInfo->pvLinAddrKM
                                                + (psTACmd->sCtlTAStatusInfo[i].sStatusDevAddr.uiAddr
                                                - psKernelMemInfo->sDevVAddr.uiAddr)) = psTACmd->sCtlTAStatusInfo[i].ui32StatusValue;
@@ -720,7 +814,7 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
        }
 
 #if defined(SUPPORT_SGX_GENERALISED_SYNCOBJECTS)
-       
+       /* SRC and DST dependencies */
        for (i=0; i<psCCBKick->ui32NumTASrcSyncs; i++)
        {
                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *) psCCBKick->ahTASrcKernelSyncInfo[i];
@@ -736,14 +830,14 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *) psCCBKick->ah3DSrcKernelSyncInfo[i];
                psSyncInfo->psSyncData->ui32ReadOpsComplete =  psSyncInfo->psSyncData->ui32ReadOpsPending;
        }
-#else
-       
+#else/* SUPPORT_SGX_GENERALISED_SYNCOBJECTS */
+       /* texture dependencies */
        for (i=0; i<psCCBKick->ui32NumSrcSyncs; i++)
        {
                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *) psCCBKick->ahSrcKernelSyncInfo[i];
                psSyncInfo->psSyncData->ui32ReadOpsComplete =  psSyncInfo->psSyncData->ui32ReadOpsPending;
        }
-#endif
+#endif/* SUPPORT_SGX_GENERALISED_SYNCOBJECTS */
 
        if (psCCBKick->bTerminateOrAbort)
        {
@@ -761,12 +855,12 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
                        }
                }
 
-               
+               /* Copy status vals over */
                for (i = 0; i < psCCBKick->ui32Num3DStatusVals; i++)
                {
 #if defined(SUPPORT_SGX_NEW_STATUS_VALS)
                        PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo = (PVRSRV_KERNEL_MEM_INFO*)psCCBKick->as3DStatusUpdate[i].hKernelMemInfo;
-                       
+                       /* derive offset into meminfo and write the status value */
                        *(IMG_UINT32*)((IMG_UINTPTR_T)psKernelMemInfo->pvLinAddrKM
                                                        + (psTACmd->sCtl3DStatusInfo[i].sStatusDevAddr.uiAddr
                                                        - psKernelMemInfo->sDevVAddr.uiAddr)) = psTACmd->sCtl3DStatusInfo[i].ui32StatusValue;
@@ -782,3 +876,6 @@ PVRSRV_ERROR SGXDoKickKM(IMG_HANDLE hDevHandle, SGX_CCB_KICK *psCCBKick)
        return eError;
 }
 
+/******************************************************************************
+ End of file (sgxkick.c)
+******************************************************************************/
index 3947cdd..d2549bb 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device specific power routines
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <stddef.h>
 
@@ -39,9 +54,10 @@ static PVRSRV_ERROR SGXAddTimer(PVRSRV_DEVICE_NODE           *psDeviceNode,
                                                                SGX_TIMING_INFORMATION  *psSGXTimingInfo,
                                                                IMG_HANDLE                              *phTimer)
 {
-       
-
-
+       /*
+               Install timer callback for HW recovery at 50 times lower
+               frequency than the microkernel timer.
+       */
        *phTimer = OSAddTimer(SGXOSTimer, psDeviceNode,
                                                  1000 * 50 / psSGXTimingInfo->ui32uKernelFreq);
        if(*phTimer == IMG_NULL)
@@ -52,9 +68,23 @@ static PVRSRV_ERROR SGXAddTimer(PVRSRV_DEVICE_NODE           *psDeviceNode,
 
        return PVRSRV_OK;
 }
-#endif 
+#endif /* SUPPORT_HW_RECOVERY*/
+
+
+/*!
+******************************************************************************
+
+ @Function     SGXUpdateTimingInfo
+
+ @Description
+
+       Derives the microkernel timing info from the system-supplied values
 
+ @Input           psDeviceNode : SGX Device node
 
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 static PVRSRV_ERROR SGXUpdateTimingInfo(PVRSRV_DEVICE_NODE     *psDeviceNode)
 {
        PVRSRV_SGXDEV_INFO      *psDevInfo = psDeviceNode->pvDevice;
@@ -86,8 +116,9 @@ static PVRSRV_ERROR SGXUpdateTimingInfo(PVRSRV_DEVICE_NODE   *psDeviceNode)
                        ui32OlduKernelFreq = psDevInfo->ui32CoreClockSpeed / psDevInfo->ui32uKernelTimerClock;
                        if (ui32OlduKernelFreq != psSGXTimingInfo->ui32uKernelFreq)
                        {
-                               
-
+                               /*
+                                       The ukernel timer frequency has changed.
+                               */
                                IMG_HANDLE hNewTimer;
                                
                                eError = SGXAddTimer(psDeviceNode, psSGXTimingInfo, &hNewTimer);
@@ -102,7 +133,7 @@ static PVRSRV_ERROR SGXUpdateTimingInfo(PVRSRV_DEVICE_NODE  *psDeviceNode)
                                }
                                else
                                {
-                                       
+                                       /* Failed to allocate the new timer, leave the old one. */
                                }
                        }
                }
@@ -118,13 +149,13 @@ static PVRSRV_ERROR SGXUpdateTimingInfo(PVRSRV_DEVICE_NODE        *psDeviceNode)
                psDevInfo->psSGXHostCtl->ui32HWRecoverySampleRate =
                        psSGXTimingInfo->ui32uKernelFreq / psSGXTimingInfo->ui32HWRecoveryFreq;
        }
-#endif 
+#endif /* SUPPORT_HW_RECOVERY*/
 
-       
+       /* Copy the SGX clock speed for use in the kernel */
        psDevInfo->ui32CoreClockSpeed = psSGXTimingInfo->ui32CoreClockSpeed;
        psDevInfo->ui32uKernelTimerClock = psSGXTimingInfo->ui32CoreClockSpeed / psSGXTimingInfo->ui32uKernelFreq;
 
-       
+       /* FIXME: no need to duplicate - remove it from psDevInfo */
        psDevInfo->psSGXHostCtl->ui32uKernelTimerClock = psDevInfo->ui32uKernelTimerClock;
 #if defined(PDUMP)
        PDUMPCOMMENT("Host Control - Microkernel clock");
@@ -132,19 +163,20 @@ static PVRSRV_ERROR SGXUpdateTimingInfo(PVRSRV_DEVICE_NODE        *psDeviceNode)
                         offsetof(SGXMKIF_HOST_CTL, ui32uKernelTimerClock),
                         sizeof(IMG_UINT32), PDUMP_FLAGS_CONTINUOUS,
                         MAKEUNIQUETAG(psDevInfo->psKernelSGXHostCtlMemInfo));
-#endif 
+#endif /* PDUMP */
 
        if (psSGXTimingInfo->bEnableActivePM)
        {
                ui32ActivePowManSampleRate =
                        psSGXTimingInfo->ui32uKernelFreq * psSGXTimingInfo->ui32ActivePowManLatencyms / 1000;
-               
-
-
-
-
-
-
+               /*
+                       ui32ActivePowerCounter has the value 0 when SGX is not idle.
+                       When SGX becomes idle, the value of ui32ActivePowerCounter is changed from 0 to ui32ActivePowManSampleRate.
+                       The ukernel timer routine decrements the value of ui32ActivePowerCounter if it is not 0.
+                       When the ukernel timer decrements ui32ActivePowerCounter from 1 to 0, the ukernel timer will
+                               request power down.
+                       Therefore the minimum value of ui32ActivePowManSampleRate is 1.
+               */
                ui32ActivePowManSampleRate += 1;
        }
        else
@@ -158,12 +190,26 @@ static PVRSRV_ERROR SGXUpdateTimingInfo(PVRSRV_DEVICE_NODE        *psDeviceNode)
                         offsetof(SGXMKIF_HOST_CTL, ui32ActivePowManSampleRate),
                         sizeof(IMG_UINT32), PDUMP_FLAGS_CONTINUOUS,
                         MAKEUNIQUETAG(psDevInfo->psKernelSGXHostCtlMemInfo));
-#endif 
+#endif /* PDUMP */
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXStartTimer
+
+ @Description
+
+       Start the microkernel timer
+
+ @Input           psDevInfo : SGX Device Info
+
+ @Return   IMG_VOID :
+
+******************************************************************************/
 static IMG_VOID SGXStartTimer(PVRSRV_SGXDEV_INFO       *psDevInfo)
 {
        #if defined(SUPPORT_HW_RECOVERY)
@@ -176,10 +222,27 @@ static IMG_VOID SGXStartTimer(PVRSRV_SGXDEV_INFO  *psDevInfo)
        }
        #else
        PVR_UNREFERENCED_PARAMETER(psDevInfo);
-       #endif 
+       #endif /* SUPPORT_HW_RECOVERY */
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXPollForClockGating
+
+ @Description
+
+       Wait until the SGX core clocks have gated.
+
+ @Input           psDevInfo : SGX Device Info
+ @Input           ui32Register : Offset of register to poll
+ @Input           ui32Register : Value of register to poll for
+ @Input           pszComment : Description of poll
+
+ @Return   IMG_VOID :
+
+******************************************************************************/
 static IMG_VOID SGXPollForClockGating (PVRSRV_SGXDEV_INFO      *psDevInfo,
                                                                           IMG_UINT32                   ui32Register,
                                                                           IMG_UINT32                   ui32RegisterValue,
@@ -193,7 +256,7 @@ static IMG_VOID SGXPollForClockGating (PVRSRV_SGXDEV_INFO   *psDevInfo,
        #if !defined(NO_HARDWARE)
        PVR_ASSERT(psDevInfo != IMG_NULL);
 
-        
+       /* PRQA S 0505 1 */ /* QAC does not like assert() */
        if (PollForValueKM((IMG_UINT32 *)psDevInfo->pvRegsBaseKM + (ui32Register >> 2),
                                                0,
                                                ui32RegisterValue,
@@ -202,15 +265,32 @@ static IMG_VOID SGXPollForClockGating (PVRSRV_SGXDEV_INFO *psDevInfo,
                                                IMG_FALSE) != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"SGXPollForClockGating: %s failed.", pszComment));
+               SGXDumpDebugInfo(psDevInfo, IMG_FALSE);
                PVR_DBG_BREAK;
        }
-       #endif 
+       #endif /* NO_HARDWARE */
 
        PDUMPCOMMENT("%s", pszComment);
        PDUMPREGPOL(SGX_PDUMPREG_NAME, ui32Register, 0, ui32RegisterValue, PDUMP_POLL_OPERATOR_EQUAL);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXPrePowerState
+
+ @Description
+
+ does necessary preparation before power state transition
+
+ @Input           hDevHandle : SGX Device Node
+ @Input           eNewPowerState : New power state
+ @Input           eCurrentPowerState : Current power state
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                              hDevHandle,
                                                           PVRSRV_DEV_POWER_STATE       eNewPowerState,
                                                           PVRSRV_DEV_POWER_STATE       eCurrentPowerState)
@@ -227,25 +307,25 @@ PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                         hDevHandle,
                IMG_UINT32                      ui32CoresEnabled;
 
                #if defined(SUPPORT_HW_RECOVERY)
-               
+               /* Disable timer callback for HW recovery */
                eError = OSDisableTimer(psDevInfo->hTimer);
                if (eError != PVRSRV_OK)
                {
                        PVR_DPF((PVR_DBG_ERROR,"SGXPrePowerState: Failed to disable timer"));
                        return eError;
                }
-               #endif 
+               #endif /* SUPPORT_HW_RECOVERY */
 
                if (eNewPowerState == PVRSRV_DEV_POWER_STATE_OFF)
                {
-                       
+                       /* Request the ukernel to idle SGX and save its state. */
                        ui32PowerCmd = PVRSRV_POWERCMD_POWEROFF;
                        ui32CompleteStatus = PVRSRV_USSE_EDM_POWMAN_POWEROFF_COMPLETE;
                        PDUMPCOMMENT("SGX power off request");
                }
                else
                {
-                       
+                       /* Request the ukernel to idle SGX. */
                        ui32PowerCmd = PVRSRV_POWERCMD_IDLE;
                        ui32CompleteStatus = PVRSRV_USSE_EDM_POWMAN_IDLE_COMPLETE;
                        PDUMPCOMMENT("SGX idle request");
@@ -260,7 +340,7 @@ PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                           hDevHandle,
                        return eError;
                }
 
-               
+               /* Wait for the ukernel to complete processing. */
                #if !defined(NO_HARDWARE)
                if (PollForValueKM(&psDevInfo->psSGXHostCtl->ui32PowerStatus,
                                                        ui32CompleteStatus,
@@ -270,9 +350,10 @@ PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                          hDevHandle,
                                                        IMG_FALSE) != PVRSRV_OK)
                {
                        PVR_DPF((PVR_DBG_ERROR,"SGXPrePowerState: Wait for SGX ukernel power transition failed."));
+                       SGXDumpDebugInfo(psDevInfo, IMG_FALSE);
                        PVR_DBG_BREAK;
                }
-               #endif 
+               #endif /* NO_HARDWARE */
 
                #if defined(PDUMP)
                PDUMPCOMMENT("TA/3D CCB Control - Wait for power event on uKernel.");
@@ -283,7 +364,7 @@ PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                           hDevHandle,
                                        PDUMP_POLL_OPERATOR_EQUAL,
                                        0,
                                        MAKEUNIQUETAG(psDevInfo->psKernelSGXHostCtlMemInfo));
-               #endif 
+               #endif /* PDUMP */
 
 #if defined(SGX_FEATURE_MP)
                ui32CoresEnabled = ((OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_CORE) & EUR_CR_MASTER_CORE_ENABLE_MASK) >> EUR_CR_MASTER_CORE_ENABLE_SHIFT) + 1;
@@ -293,7 +374,7 @@ PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                           hDevHandle,
 
                for (ui32Core = 0; ui32Core < ui32CoresEnabled; ui32Core++)
                {
-                       
+                       /* Wait for SGX clock gating. */
                        SGXPollForClockGating(psDevInfo,
                                                                  SGX_MP_CORE_SELECT(psDevInfo->ui32ClkGateStatusReg, ui32Core),
                                                                  psDevInfo->ui32ClkGateStatusMask,
@@ -301,7 +382,7 @@ PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                           hDevHandle,
                }
 
                #if defined(SGX_FEATURE_MP)
-               
+               /* Wait for SGX master clock gating. */
                SGXPollForClockGating(psDevInfo,
                                                          psDevInfo->ui32MasterClkGateStatusReg,
                                                          psDevInfo->ui32MasterClkGateStatusMask,
@@ -311,11 +392,11 @@ PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                         hDevHandle,
                                                          psDevInfo->ui32MasterClkGateStatus2Reg,
                                                          psDevInfo->ui32MasterClkGateStatus2Mask,
                                                          "Wait for SGX master clock gating (2)");
-               #endif 
+               #endif /* SGX_FEATURE_MP */
 
                if (eNewPowerState == PVRSRV_DEV_POWER_STATE_OFF)
                {
-                       
+                       /* Finally, de-initialise some registers. */
                        eError = SGXDeinitialise(psDevInfo);
                        if (eError != PVRSRV_OK)
                        {
@@ -329,6 +410,22 @@ PVRSRV_ERROR SGXPrePowerState (IMG_HANDLE                          hDevHandle,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXPostPowerState
+
+ @Description
+
+ does necessary preparation after power state transition
+
+ @Input           hDevHandle : SGX Device Node
+ @Input           eNewPowerState : New power state
+ @Input           eCurrentPowerState : Current power state
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 PVRSRV_ERROR SGXPostPowerState (IMG_HANDLE                             hDevHandle,
                                                                PVRSRV_DEV_POWER_STATE  eNewPowerState,
                                                                PVRSRV_DEV_POWER_STATE  eCurrentPowerState)
@@ -341,7 +438,7 @@ PVRSRV_ERROR SGXPostPowerState (IMG_HANDLE                          hDevHandle,
                PVRSRV_SGXDEV_INFO      *psDevInfo = psDeviceNode->pvDevice;
                SGXMKIF_HOST_CTL *psSGXHostCtl = psDevInfo->psSGXHostCtl;
 
-               
+               /* Reset the power manager flags. */
                psSGXHostCtl->ui32PowerStatus = 0;
                #if defined(PDUMP)
                PDUMPCOMMENT("Host Control - Reset power status");
@@ -349,14 +446,17 @@ PVRSRV_ERROR SGXPostPowerState (IMG_HANDLE                                hDevHandle,
                                 offsetof(SGXMKIF_HOST_CTL, ui32PowerStatus),
                                 sizeof(IMG_UINT32), PDUMP_FLAGS_CONTINUOUS,
                                 MAKEUNIQUETAG(psDevInfo->psKernelSGXHostCtlMemInfo));
-               #endif 
+               #endif /* PDUMP */
 
                if (eCurrentPowerState == PVRSRV_DEV_POWER_STATE_OFF)
                {
-                       
-
-                       
+                       /*
+                               Coming up from off, re-initialise SGX.
+                       */
 
+                       /*
+                               Re-generate the timing data required by SGX.
+                       */
                        eError = SGXUpdateTimingInfo(psDeviceNode);
                        if (eError != PVRSRV_OK)
                        {
@@ -364,8 +464,9 @@ PVRSRV_ERROR SGXPostPowerState (IMG_HANDLE                          hDevHandle,
                                return eError;
                        }
 
-                       
-
+                       /*
+                               Run the SGX init script.
+                       */
                        eError = SGXInitialise(psDevInfo, IMG_FALSE);
                        if (eError != PVRSRV_OK)
                        {
@@ -375,8 +476,9 @@ PVRSRV_ERROR SGXPostPowerState (IMG_HANDLE                          hDevHandle,
                }
                else
                {
-                       
-
+                       /*
+                               Coming up from idle, restart the ukernel.
+                       */
                        SGXMKIF_COMMAND         sCommand = {0};
 
                        sCommand.ui32Data[1] = PVRSRV_POWERCMD_RESUME;
@@ -395,6 +497,22 @@ PVRSRV_ERROR SGXPostPowerState (IMG_HANDLE                         hDevHandle,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXPreClockSpeedChange
+
+ @Description
+
+       Does processing required before an SGX clock speed change.
+
+ @Input           hDevHandle : SGX Device Node
+ @Input           bIdleDevice : Whether the microkernel needs to be idled
+ @Input           eCurrentPowerState : Power state of the device
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 PVRSRV_ERROR SGXPreClockSpeedChange (IMG_HANDLE                                hDevHandle,
                                                                         IMG_BOOL                               bIdleDevice,
                                                                         PVRSRV_DEV_POWER_STATE eCurrentPowerState)
@@ -409,7 +527,9 @@ PVRSRV_ERROR SGXPreClockSpeedChange (IMG_HANDLE                             hDevHandle,
        {
                if (bIdleDevice)
                {
-                       
+                       /*
+                        * Idle SGX.
+                        */
                        PDUMPSUSPEND();
 
                        eError = SGXPrePowerState(hDevHandle, PVRSRV_DEV_POWER_STATE_IDLE,
@@ -430,6 +550,22 @@ PVRSRV_ERROR SGXPreClockSpeedChange (IMG_HANDLE                            hDevHandle,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXPostClockSpeedChange
+
+ @Description
+
+       Does processing required after an SGX clock speed change.
+
+ @Input           hDevHandle : SGX Device Node
+ @Input           bIdleDevice : Whether the microkernel had been idled previously
+ @Input           eCurrentPowerState : Power state of the device
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 PVRSRV_ERROR SGXPostClockSpeedChange (IMG_HANDLE                               hDevHandle,
                                                                          IMG_BOOL                                      bIdleDevice,
                                                                          PVRSRV_DEV_POWER_STATE        eCurrentPowerState)
@@ -444,8 +580,9 @@ PVRSRV_ERROR SGXPostClockSpeedChange (IMG_HANDLE                            hDevHandle,
        {
                PVRSRV_ERROR eError;
 
-               
-
+               /*
+                       Re-generate the timing data required by SGX.
+               */
                eError = SGXUpdateTimingInfo(psDeviceNode);
                if (eError != PVRSRV_OK)
                {
@@ -455,7 +592,9 @@ PVRSRV_ERROR SGXPostClockSpeedChange (IMG_HANDLE                            hDevHandle,
 
                if (bIdleDevice)
                {
-                       
+                       /*
+                        * Resume SGX.
+                        */
                        eError = SGXPostPowerState(hDevHandle, PVRSRV_DEV_POWER_STATE_ON,
                                                                           PVRSRV_DEV_POWER_STATE_IDLE);
 
@@ -479,3 +618,6 @@ PVRSRV_ERROR SGXPostClockSpeedChange (IMG_HANDLE                            hDevHandle,
 }
 
 
+/******************************************************************************
+ End of file (sgxpower.c)
+******************************************************************************/
index 519783f..dcdefae 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device specific reset routines
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "sgxdefs.h"
 #include "sgxmmu.h"
 #include "pdump_km.h"
 
 
+/*!
+*******************************************************************************
+
+ @Function     SGXInitClocks
+
+ @Description
+       Initialise the SGX clocks
+
+ @Input psDevInfo - device info. structure
+ @Input ui32PDUMPFlags - flags to control PDUMP output
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 IMG_VOID SGXInitClocks(PVRSRV_SGXDEV_INFO      *psDevInfo,
                                           IMG_UINT32                   ui32PDUMPFlags)
 {
@@ -41,7 +70,7 @@ IMG_VOID SGXInitClocks(PVRSRV_SGXDEV_INFO     *psDevInfo,
        
 #if !defined(PDUMP)
        PVR_UNREFERENCED_PARAMETER(ui32PDUMPFlags);
-#endif 
+#endif /* PDUMP */
        
        ui32RegVal = psDevInfo->ui32ClkGateCtl;
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_CLKGATECTL, ui32RegVal);
@@ -55,6 +84,19 @@ IMG_VOID SGXInitClocks(PVRSRV_SGXDEV_INFO    *psDevInfo,
 }
 
 
+/*!
+*******************************************************************************
+
+ @Function     SGXResetInitBIFContexts
+
+ @Description
+       Initialise the BIF memory contexts
+
+ @Input psDevInfo - SGX Device Info
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 static IMG_VOID SGXResetInitBIFContexts(PVRSRV_SGXDEV_INFO     *psDevInfo,
                                                                                IMG_UINT32                      ui32PDUMPFlags)
 {
@@ -62,7 +104,7 @@ static IMG_VOID SGXResetInitBIFContexts(PVRSRV_SGXDEV_INFO   *psDevInfo,
 
 #if !defined(PDUMP)
        PVR_UNREFERENCED_PARAMETER(ui32PDUMPFlags);
-#endif 
+#endif /* PDUMP */
 
        ui32RegVal = 0;
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32RegVal);
@@ -74,7 +116,7 @@ static IMG_VOID SGXResetInitBIFContexts(PVRSRV_SGXDEV_INFO   *psDevInfo,
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_BANK_SET, ui32RegVal, ui32PDUMPFlags);
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_BANK0, ui32RegVal);
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_BANK0, ui32RegVal, ui32PDUMPFlags);
-#endif 
+#endif /* SGX_FEATURE_MULTIPLE_MEM_CONTEXTS */
 
        PDUMPCOMMENTWITHFLAGS(ui32PDUMPFlags, "Initialise the BIF directory list\r\n");
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_DIR_LIST_BASE0, ui32RegVal);
@@ -93,10 +135,23 @@ static IMG_VOID SGXResetInitBIFContexts(PVRSRV_SGXDEV_INFO *psDevInfo,
                        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, ui32DirListReg, ui32RegVal, ui32PDUMPFlags);
                }
        }
-#endif 
+#endif /* SGX_FEATURE_MULTIPLE_MEM_CONTEXTS */
 }
 
 
+/*!
+*******************************************************************************
+
+ @Function     SGXResetSetupBIFContexts
+
+ @Description
+       Configure the BIF for the EDM context
+
+ @Input psDevInfo - SGX Device Info
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 static IMG_VOID SGXResetSetupBIFContexts(PVRSRV_SGXDEV_INFO    *psDevInfo,
                                                                                 IMG_UINT32                     ui32PDUMPFlags)
 {
@@ -104,37 +159,37 @@ static IMG_VOID SGXResetSetupBIFContexts(PVRSRV_SGXDEV_INFO       *psDevInfo,
 
 #if !defined(PDUMP)
        PVR_UNREFERENCED_PARAMETER(ui32PDUMPFlags);
-#endif 
+#endif /* PDUMP */
        
        #if defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS)
-       
+       /* Set up EDM for bank 0 to point at kernel context */
        ui32RegVal = (SGX_BIF_DIR_LIST_INDEX_EDM << EUR_CR_BIF_BANK0_INDEX_EDM_SHIFT);
 
        #if defined(SGX_FEATURE_2D_HARDWARE) && !defined(SGX_FEATURE_PTLA)
-       
+       /* Set up 2D core for bank 0 to point at kernel context */
        ui32RegVal |= (SGX_BIF_DIR_LIST_INDEX_EDM << EUR_CR_BIF_BANK0_INDEX_2D_SHIFT);
-       #endif 
+       #endif /* SGX_FEATURE_2D_HARDWARE */
 
        #if defined(FIX_HW_BRN_23410)
-       
+       /* Set up TA core for bank 0 to point at kernel context to guarantee it is a valid context */
        ui32RegVal |= (SGX_BIF_DIR_LIST_INDEX_EDM << EUR_CR_BIF_BANK0_INDEX_TA_SHIFT);
-       #endif 
+       #endif /* FIX_HW_BRN_23410 */
 
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_BANK0, ui32RegVal);
        PDUMPCOMMENTWITHFLAGS(ui32PDUMPFlags, "Set up EDM requestor page table in BIF\r\n");
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_BANK0, ui32RegVal, ui32PDUMPFlags);
-       #endif 
+       #endif /* defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS) */
 
        {
                IMG_UINT32      ui32EDMDirListReg;
 
-               
+               /* Set up EDM context with kernel page directory */
                #if (SGX_BIF_DIR_LIST_INDEX_EDM == 0)
                ui32EDMDirListReg = EUR_CR_BIF_DIR_LIST_BASE0;
                #else
-               
+               /* Bases 0 and 1 are not necessarily contiguous */
                ui32EDMDirListReg = EUR_CR_BIF_DIR_LIST_BASE1 + 4 * (SGX_BIF_DIR_LIST_INDEX_EDM - 1);
-               #endif 
+               #endif /* SGX_BIF_DIR_LIST_INDEX_EDM */
 
                ui32RegVal = psDevInfo->sKernelPDDevPAddr.uiAddr >> SGX_MMU_PDE_ADDR_ALIGNSHIFT;
                
@@ -150,6 +205,23 @@ static IMG_VOID SGXResetSetupBIFContexts(PVRSRV_SGXDEV_INFO        *psDevInfo,
 }
 
 
+/*!
+*******************************************************************************
+
+ @Function     SGXResetSleep
+
+ @Description
+
+ Sleep for a short time to allow reset register writes to complete.
+ Required because no status registers are available to poll on.
+
+ @Input psDevInfo - SGX Device Info
+ @Input ui32PDUMPFlags - flags to control PDUMP output
+ @Input bPDump - Pdump the sleep
+
+ @Return   Nothing
+
+******************************************************************************/
 static IMG_VOID SGXResetSleep(PVRSRV_SGXDEV_INFO       *psDevInfo,
                                                          IMG_UINT32                    ui32PDUMPFlags,
                                                          IMG_BOOL                              bPDump)
@@ -161,14 +233,14 @@ static IMG_VOID SGXResetSleep(PVRSRV_SGXDEV_INFO  *psDevInfo,
        ui32ReadRegister = EUR_CR_MASTER_SOFT_RESET;
        #else
        ui32ReadRegister = EUR_CR_SOFT_RESET;
-       #endif 
+       #endif /* SGX_FEATURE_MP */
 #endif
 
 #if !defined(PDUMP)
        PVR_UNREFERENCED_PARAMETER(ui32PDUMPFlags);
-#endif 
+#endif /* PDUMP */
 
-       
+       /* Sleep for 100 SGX clocks */
        SGXWaitClocks(psDevInfo, 100);
        if (bPDump)
        {
@@ -180,14 +252,32 @@ static IMG_VOID SGXResetSleep(PVRSRV_SGXDEV_INFO  *psDevInfo,
        }
 
 #if defined(EMULATOR)
-       
-
+       /*
+               Read a register to make sure we wait long enough on the emulator...
+       */
        OSReadHWReg(psDevInfo->pvRegsBaseKM, ui32ReadRegister);
 #endif
 }
 
 
 #if !defined(SGX_FEATURE_MP)
+/*!
+*******************************************************************************
+
+ @Function     SGXResetSoftReset
+
+ @Description
+
+ Write to the SGX soft reset register.
+
+ @Input psDevInfo - SGX Device Info
+ @Input bResetBIF - Include the BIF in the soft reset
+ @Input ui32PDUMPFlags - flags to control PDUMP output
+ @Input bPDump - Pdump the sleep
+
+ @Return   Nothing
+
+******************************************************************************/
 static IMG_VOID SGXResetSoftReset(PVRSRV_SGXDEV_INFO   *psDevInfo,
                                                                  IMG_BOOL                              bResetBIF,
                                                                  IMG_UINT32                    ui32PDUMPFlags,
@@ -196,13 +286,14 @@ static IMG_VOID SGXResetSoftReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
        IMG_UINT32 ui32SoftResetRegVal;
 
        ui32SoftResetRegVal =
-                                       
+                                       /* add common reset bits: */
                                        EUR_CR_SOFT_RESET_DPM_RESET_MASK |
                                        EUR_CR_SOFT_RESET_TA_RESET_MASK  |
                                        EUR_CR_SOFT_RESET_USE_RESET_MASK |
                                        EUR_CR_SOFT_RESET_ISP_RESET_MASK |
                                        EUR_CR_SOFT_RESET_TSP_RESET_MASK;
 
+/* add conditional reset bits: */
 #ifdef EUR_CR_SOFT_RESET_TWOD_RESET_MASK
        ui32SoftResetRegVal |= EUR_CR_SOFT_RESET_TWOD_RESET_MASK;
 #endif
@@ -254,7 +345,7 @@ static IMG_VOID SGXResetSoftReset(PVRSRV_SGXDEV_INFO        *psDevInfo,
 
 #if !defined(PDUMP)
        PVR_UNREFERENCED_PARAMETER(ui32PDUMPFlags);
-#endif 
+#endif /* PDUMP */
 
        if (bResetBIF)
        {
@@ -269,13 +360,28 @@ static IMG_VOID SGXResetSoftReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
 }
 
 
+/*!
+*******************************************************************************
+
+ @Function     SGXResetInvalDC
+
+ @Description
+
+ Invalidate the BIF Directory Cache and wait for the operation to complete.
+
+ @Input psDevInfo - SGX Device Info
+ @Input ui32PDUMPFlags - flags to control PDUMP output
+
+ @Return   Nothing
+
+******************************************************************************/
 static IMG_VOID SGXResetInvalDC(PVRSRV_SGXDEV_INFO     *psDevInfo,
                                                            IMG_UINT32                  ui32PDUMPFlags,
                                                                IMG_BOOL                        bPDump)
 {
        IMG_UINT32 ui32RegVal;
 
-       
+       /* Invalidate BIF Directory cache. */
 #if defined(EUR_CR_BIF_CTRL_INVAL)
        ui32RegVal = EUR_CR_BIF_CTRL_INVAL_ALL_MASK;
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL_INVAL, ui32RegVal);
@@ -302,9 +408,10 @@ static IMG_VOID SGXResetInvalDC(PVRSRV_SGXDEV_INFO *psDevInfo,
 
 #if !defined(SGX_FEATURE_MULTIPLE_MEM_CONTEXTS)
        {
-               
-
-
+               /*
+                       Wait for the DC invalidate to complete - indicated by
+                       outstanding reads reaching zero.
+               */
                if (PollForValueKM((IMG_UINT32 *)((IMG_UINT8*)psDevInfo->pvRegsBaseKM + EUR_CR_BIF_MEM_REQ_STAT),
                                                        0,
                                                        EUR_CR_BIF_MEM_REQ_STAT_READS_MASK,
@@ -321,11 +428,28 @@ static IMG_VOID SGXResetInvalDC(PVRSRV_SGXDEV_INFO        *psDevInfo,
                        PDUMPREGPOLWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_MEM_REQ_STAT, 0, EUR_CR_BIF_MEM_REQ_STAT_READS_MASK, ui32PDUMPFlags, PDUMP_POLL_OPERATOR_EQUAL);
                }
        }
-#endif 
+#endif /* SGX_FEATURE_MULTIPLE_MEM_CONTEXTS */
 }
-#endif 
+#endif /* SGX_FEATURE_MP */
+
+
+/*!
+*******************************************************************************
 
+ @Function     SGXReset
 
+ @Description
+
+ Reset chip
+
+ @Input psDevInfo - device info. structure
+ @Input bHardwareRecovery - true if recovering powered hardware,
+                                                       false if powering up
+ @Input ui32PDUMPFlags - flags to control PDUMP output
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO   *psDevInfo,
                                  IMG_BOOL                              bHardwareRecovery,
                                  IMG_UINT32                    ui32PDUMPFlags)
@@ -340,12 +464,12 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
 
 #if !defined(PDUMP)
        PVR_UNREFERENCED_PARAMETER(ui32PDUMPFlags);
-#endif 
+#endif /* PDUMP */
 
        PDUMPCOMMENTWITHFLAGS(ui32PDUMPFlags, "Start of SGX reset sequence\r\n");
 
 #if defined(FIX_HW_BRN_23944)
-       
+       /* Pause the BIF. */
        ui32RegVal = EUR_CR_BIF_CTRL_PAUSE_MASK;
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32RegVal);
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_CTRL, ui32RegVal, ui32PDUMPFlags);
@@ -355,7 +479,7 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO        *psDevInfo,
        ui32RegVal = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_INT_STAT);
        if (ui32RegVal & ui32BifFaultMask)
        {
-               
+               /* Page fault needs to be cleared before resetting the BIF. */
                ui32RegVal = EUR_CR_BIF_CTRL_PAUSE_MASK | EUR_CR_BIF_CTRL_CLEAR_FAULT_MASK;
                OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_CTRL, ui32RegVal);
                PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_CTRL, ui32RegVal, ui32PDUMPFlags);
@@ -368,17 +492,18 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
 
                SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_TRUE);
        }
-#endif 
+#endif /* defined(FIX_HW_BRN_23944) */
 
-       
+       /* Reset all including BIF */
        SGXResetSoftReset(psDevInfo, IMG_TRUE, ui32PDUMPFlags, IMG_TRUE);
 
        SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_TRUE);
 
-       
-
+       /*
+               Initialise the BIF state.
+       */
 #if defined(SGX_FEATURE_36BIT_MMU)
-       
+       /* enable 36bit addressing mode if the MMU supports it*/
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_36BIT_ADDRESSING, EUR_CR_BIF_36BIT_ADDRESSING_ENABLE_MASK);
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_36BIT_ADDRESSING, EUR_CR_BIF_36BIT_ADDRESSING_ENABLE_MASK, ui32PDUMPFlags);
 #endif
@@ -386,57 +511,60 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
        SGXResetInitBIFContexts(psDevInfo, ui32PDUMPFlags);
 
 #if defined(EUR_CR_BIF_MEM_ARB_CONFIG)
-       
-
+       /*
+               Initialise the memory arbiter to its default state
+       */
        ui32RegVal      = (12UL << EUR_CR_BIF_MEM_ARB_CONFIG_PAGE_SIZE_SHIFT) |
                                  (7UL << EUR_CR_BIF_MEM_ARB_CONFIG_BEST_CNT_SHIFT) |
                                  (12UL << EUR_CR_BIF_MEM_ARB_CONFIG_TTE_THRESH_SHIFT);
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_MEM_ARB_CONFIG, ui32RegVal);
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_MEM_ARB_CONFIG, ui32RegVal, ui32PDUMPFlags);
-#endif 
+#endif /* EUR_CR_BIF_MEM_ARB_CONFIG */
 
 #if defined(SGX_FEATURE_SYSTEM_CACHE)
        #if defined(SGX_BYPASS_SYSTEM_CACHE)
-               
+               /* set the SLC to bypass all accesses */
                ui32RegVal = MNE_CR_CTRL_BYPASS_ALL_MASK;
        #else
                #if defined(FIX_HW_BRN_26620)
                        ui32RegVal = 0;
                #else
-                       
+                       /* set the SLC to bypass cache-coherent accesses */
                        ui32RegVal = MNE_CR_CTRL_BYP_CC_MASK;
                #endif
                #if defined(FIX_HW_BRN_34028)
-                       
+                       /* Bypass the MNE for the USEC requester */
                        ui32RegVal |= (8 << MNE_CR_CTRL_BYPASS_SHIFT);
                #endif
-       #endif 
+       #endif /* SGX_BYPASS_SYSTEM_CACHE */
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, MNE_CR_CTRL, ui32RegVal);
        PDUMPREG(SGX_PDUMPREG_NAME, MNE_CR_CTRL, ui32RegVal);
-#endif 
+#endif /* SGX_FEATURE_SYSTEM_CACHE */
 
        if (bHardwareRecovery)
        {
-               
-
-
-
-
-
-
+               /*
+                       Set all requestors to the dummy PD which forces all memory
+                       accesses to page fault.
+                       This enables us to flush out BIF requests from parts of SGX
+                       which do not have their own soft reset.
+                       Note: sBIFResetPDDevPAddr.uiAddr is a relative address (2GB max)
+                       MSB is the bus master flag; 1 == enabled
+               */
                ui32RegVal = (IMG_UINT32)psDevInfo->sBIFResetPDDevPAddr.uiAddr;
                OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_DIR_LIST_BASE0, ui32RegVal);
 
                SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_FALSE);
 
-               
+               /* Bring BIF out of reset. */
                SGXResetSoftReset(psDevInfo, IMG_FALSE, ui32PDUMPFlags, IMG_TRUE);
                SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_FALSE);
 
                SGXResetInvalDC(psDevInfo, ui32PDUMPFlags, IMG_FALSE);
 
-               
-
+               /*
+                       Check for a page fault from parts of SGX which do not have a reset.
+               */
                for (;;)
                {
                        IMG_UINT32 ui32BifIntStat = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_INT_STAT);
@@ -448,18 +576,19 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
                                break;
                        }
 
-                       
-
-
+                       /*
+                               There is a page fault, so reset the BIF again, map in the dummy page,
+                               bring the BIF up and invalidate the Directory Cache.
+                       */
                        sBifFault.uiAddr = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_FAULT);
                        PVR_DPF((PVR_DBG_WARNING, "SGXReset: Page fault 0x%x/0x%x", ui32BifIntStat, sBifFault.uiAddr));
                        ui32PDIndex = sBifFault.uiAddr >> (SGX_MMU_PAGE_SHIFT + SGX_MMU_PT_SHIFT);
                        ui32PTIndex = (sBifFault.uiAddr & SGX_MMU_PT_MASK) >> SGX_MMU_PAGE_SHIFT;
 
-                       
+                       /* Put the BIF into reset. */
                        SGXResetSoftReset(psDevInfo, IMG_TRUE, ui32PDUMPFlags, IMG_FALSE);
 
-                       
+                       /* Map in the dummy page. */
                        psDevInfo->pui32BIFResetPD[ui32PDIndex] = (psDevInfo->sBIFResetPTDevPAddr.uiAddr
                                                                                                        >>SGX_MMU_PDE_ADDR_ALIGNSHIFT)
                                                                                                        | SGX_MMU_PDE_PAGE_SIZE_4K
@@ -468,7 +597,7 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO        *psDevInfo,
                                                                                                        >>SGX_MMU_PTE_ADDR_ALIGNSHIFT)
                                                                                                        | SGX_MMU_PTE_VALID;
 
-                       
+                       /* Clear outstanding events. */
                        ui32RegVal = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_STATUS);
                        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_HOST_CLEAR, ui32RegVal);
                        ui32RegVal = OSReadHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_EVENT_STATUS2);
@@ -476,50 +605,51 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
 
                        SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_FALSE);
 
-                       
+                       /* Bring the BIF out of reset. */
                        SGXResetSoftReset(psDevInfo, IMG_FALSE, ui32PDUMPFlags, IMG_FALSE);
                        SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_FALSE);
 
-                       
+                       /* Invalidate Directory Cache. */
                        SGXResetInvalDC(psDevInfo, ui32PDUMPFlags, IMG_FALSE);
 
-                       
+                       /* Unmap the dummy page and try again. */
                        psDevInfo->pui32BIFResetPD[ui32PDIndex] = 0;
                        psDevInfo->pui32BIFResetPT[ui32PTIndex] = 0;
                }
        }
        else
        {
-               
+               /* Bring BIF out of reset. */
                SGXResetSoftReset(psDevInfo, IMG_FALSE, ui32PDUMPFlags, IMG_TRUE);
                SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_FALSE);
        }       
 
-       
-
+       /*
+               Initialise the BIF memory contexts before bringing the rest of SGX out of reset.
+       */
        SGXResetSetupBIFContexts(psDevInfo, ui32PDUMPFlags);
 
 #if defined(SGX_FEATURE_2D_HARDWARE) && !defined(SGX_FEATURE_PTLA)
-       
+       /* check that the heap base has the right alignment (1Mb) */
        #if ((SGX_2D_HEAP_BASE & ~EUR_CR_BIF_TWOD_REQ_BASE_ADDR_MASK) != 0)
                #error "SGXReset: SGX_2D_HEAP_BASE doesn't match EUR_CR_BIF_TWOD_REQ_BASE_ADDR_MASK alignment"
        #endif
-       
+       /* Set up 2D requestor base */
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_BIF_TWOD_REQ_BASE, SGX_2D_HEAP_BASE);
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_BIF_TWOD_REQ_BASE, SGX_2D_HEAP_BASE, ui32PDUMPFlags);
 #endif
 
-       
+       /* Invalidate BIF Directory cache. */
        SGXResetInvalDC(psDevInfo, ui32PDUMPFlags, IMG_TRUE);
 
        PVR_DPF((PVR_DBG_MESSAGE,"Soft Reset of SGX"));
 
-       
+       /* Take chip out of reset */
        ui32RegVal = 0;
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_SOFT_RESET, ui32RegVal);
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_SOFT_RESET, ui32RegVal, ui32PDUMPFlags);
 
-       
+       /* wait a bit */
        SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_TRUE);
 
        PDUMPCOMMENTWITHFLAGS(ui32PDUMPFlags, "End of SGX reset sequence\r\n");
@@ -534,17 +664,21 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
 
 #if !defined(PDUMP)
        PVR_UNREFERENCED_PARAMETER(ui32PDUMPFlags);
-#endif 
+#endif /* PDUMP */
 
        PDUMPCOMMENTWITHFLAGS(ui32PDUMPFlags, "Start of SGX MP reset sequence\r\n");
 
-       
+       /* Put hydra into soft reset */
        ui32RegVal = EUR_CR_MASTER_SOFT_RESET_BIF_RESET_MASK  |
                                 EUR_CR_MASTER_SOFT_RESET_IPF_RESET_MASK  |
                                 EUR_CR_MASTER_SOFT_RESET_DPM_RESET_MASK  |
-                                EUR_CR_MASTER_SOFT_RESET_MCI_RESET_MASK  |
                                 EUR_CR_MASTER_SOFT_RESET_VDM_RESET_MASK;
 
+       if (bHardwareRecovery)
+       {
+               ui32RegVal |= EUR_CR_MASTER_SOFT_RESET_MCI_RESET_MASK;
+       }
+
 #if defined(SGX_FEATURE_PTLA)
        ui32RegVal |= EUR_CR_MASTER_SOFT_RESET_PTLA_RESET_MASK;
 #endif
@@ -552,7 +686,7 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO        *psDevInfo,
        ui32RegVal |= EUR_CR_MASTER_SOFT_RESET_SLC_RESET_MASK;
 #endif
 
-       
+       /* Hard reset the slave cores */
        ui32RegVal |= EUR_CR_MASTER_SOFT_RESET_CORE_RESET_MASK(0)  |
                                  EUR_CR_MASTER_SOFT_RESET_CORE_RESET_MASK(1)  |
                                  EUR_CR_MASTER_SOFT_RESET_CORE_RESET_MASK(2)  |
@@ -579,6 +713,9 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO        *psDevInfo,
                #endif
                #if defined(PVR_SLC_8KB_ADDRESS_MODE)
                                                (4 << EUR_CR_MASTER_SLC_CTRL_ADDR_DECODE_MODE_SHIFT) |
+               #endif
+               #if defined(FIX_HW_BRN_33809)
+                       (2 << EUR_CR_MASTER_SLC_CTRL_ADDR_DECODE_MODE_SHIFT) |
                #endif
                                                (0xC << EUR_CR_MASTER_SLC_CTRL_ARB_PAGE_SIZE_SHIFT);
                OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_SLC_CTRL, ui32RegVal);
@@ -596,15 +733,15 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
                                EUR_CR_MASTER_SLC_CTRL_BYPASS_REQ_USE3_MASK |
                                EUR_CR_MASTER_SLC_CTRL_BYPASS_REQ_TA_MASK;
        #endif
-       #endif 
+       #endif /* SGX_BYPASS_SYSTEM_CACHE */
                OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_SLC_CTRL_BYPASS, ui32RegVal);
                PDUMPCOMMENTWITHFLAGS(ui32PDUMPFlags, "Initialise the hydra SLC bypass control\r\n");
                PDUMPREG(SGX_PDUMPREG_NAME, EUR_CR_MASTER_SLC_CTRL_BYPASS, ui32RegVal);
-#endif 
+#endif /* SGX_FEATURE_SYSTEM_CACHE */
 
        SGXResetSleep(psDevInfo, ui32PDUMPFlags, IMG_TRUE);
 
-       
+       /* Remove the resets */
        ui32RegVal = 0;
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_SOFT_RESET, ui32RegVal);
        PDUMPCOMMENTWITHFLAGS(ui32PDUMPFlags, "Remove the resets from all of SGX\r\n");
@@ -621,32 +758,32 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO      *psDevInfo,
 
 #if defined(FIX_HW_BRN_31278) || defined(FIX_HW_BRN_31620) || defined(FIX_HW_BRN_31671) || defined(FIX_HW_BRN_32085)
        #if defined(FIX_HW_BRN_31278) || defined(FIX_HW_BRN_32085)
-       
+       /* disable prefetch */
        ui32RegVal = (1<<EUR_CR_MASTER_BIF_MMU_CTRL_ADDR_HASH_MODE_SHIFT);
        #else
        ui32RegVal = (1<<EUR_CR_MASTER_BIF_MMU_CTRL_ADDR_HASH_MODE_SHIFT) | EUR_CR_MASTER_BIF_MMU_CTRL_PREFETCHING_ON_MASK; 
        #endif
        #if !defined(FIX_HW_BRN_31620) && !defined(FIX_HW_BRN_31671)
-       
+       /* enable the DC TLB */
        ui32RegVal |= EUR_CR_MASTER_BIF_MMU_CTRL_ENABLE_DC_TLB_MASK;
        #endif
 
-       
+       /* Master bank */
        OSWriteHWReg(psDevInfo->pvRegsBaseKM, EUR_CR_MASTER_BIF_MMU_CTRL, ui32RegVal);
        PDUMPREGWITHFLAGS(SGX_PDUMPREG_NAME, EUR_CR_MASTER_BIF_MMU_CTRL, ui32RegVal, ui32PDUMPFlags);
 
        #if defined(FIX_HW_BRN_31278) || defined(FIX_HW_BRN_32085)
-       
+       /* disable prefetch */
        ui32RegVal = (1<<EUR_CR_BIF_MMU_CTRL_ADDR_HASH_MODE_SHIFT);
        #else
        ui32RegVal = (1<<EUR_CR_BIF_MMU_CTRL_ADDR_HASH_MODE_SHIFT) | EUR_CR_BIF_MMU_CTRL_PREFETCHING_ON_MASK; 
        #endif
        #if !defined(FIX_HW_BRN_31620) && !defined(FIX_HW_BRN_31671)
-       
+       /* enable the DC TLB */
        ui32RegVal |= EUR_CR_BIF_MMU_CTRL_ENABLE_DC_TLB_MASK;
        #endif
 
-       
+       /* Per-core */
        {
                IMG_UINT32 ui32Core;
 
@@ -663,6 +800,9 @@ IMG_VOID SGXReset(PVRSRV_SGXDEV_INFO        *psDevInfo,
        
        PDUMPCOMMENTWITHFLAGS(ui32PDUMPFlags, "End of SGX MP reset sequence\r\n");
 }      
-#endif 
+#endif /* SGX_FEATURE_MP */
 
 
+/******************************************************************************
+ End of file (sgxreset.c)
+******************************************************************************/
index 8a9415f..81f3b07 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device specific transfer queue routines
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if defined(TRANSFER_QUEUE)
 
@@ -64,7 +79,11 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
 
 #if defined(PDUMP)
        IMG_BOOL bPersistentProcess = IMG_FALSE;
-       
+       /*
+        *      For persistent processes, the HW kicks should not go into the
+        *      extended init phase; only keep memory transactions from the
+        *      window system which are necessary to run the client app.
+        */
        {
                PVRSRV_PER_PROCESS_DATA* psPerProc = PVRSRVFindPerProcessData();
                if(psPerProc != IMG_NULL)
@@ -72,7 +91,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                        bPersistentProcess = psPerProc->bPDumpPersistent;
                }
        }
-#endif 
+#endif /* PDUMP */
 #if defined(FIX_HW_BRN_31620)
        hDevMemContext = psKick->hDevMemContext;
 #endif
@@ -91,8 +110,8 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                                TRANSFER_TOKEN_SUBMIT);
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
-       
-       
+       /* override QAC warning about stricter alignment */
+       /* PRQA S 3305 1 */
        psSharedTransferCmd =  CCB_DATA_FROM_OFFSET(SGXMKIF_TRANSFERCMD_SHARED, psCCBMemInfo, psKick, ui32SharedCmdCCBOffset);
 
        PVR_TTRACE(PVRSRV_TRACE_GROUP_TRANSFER, PVRSRV_TRACE_CLASS_CMD_START, TRANSFER_TOKEN_SUBMIT);
@@ -137,7 +156,9 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                psSharedTransferCmd->s3DSyncReadOpsCompleteDevVAddr.uiAddr = 0;
        }
 
-       
+       /* filter out multiple occurrences of the same sync object from srcs or dests
+        * note : the same sync can still be used to synchronize both src and dst.
+        */
        for (loop = 0; loop < MIN(SGX_MAX_TRANSFER_SYNC_OPS, psKick->ui32NumSrcSync); loop++)
        {
                IMG_UINT32 i;
@@ -222,20 +243,29 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                        {
                                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psKick->ahDstSyncInfo[loop];
 
+                               psSyncInfo->psSyncData->ui64LastWrite = ui64KickCount;
+
                                PVR_TTRACE_SYNC_OBJECT(PVRSRV_TRACE_GROUP_TRANSFER, TRANSFER_TOKEN_DST_SYNC,
                                                psSyncInfo, PVRSRV_SYNCOP_SAMPLE);
 
                                psSharedTransferCmd->asDstSyncs[i].ui32WriteOpsPendingVal = psSyncInfo->psSyncData->ui32WriteOpsPending;
                                psSharedTransferCmd->asDstSyncs[i].ui32ReadOpsPendingVal = psSyncInfo->psSyncData->ui32ReadOpsPending;
+                               psSharedTransferCmd->asDstSyncs[i].ui32ReadOps2PendingVal = psSyncInfo->psSyncData->ui32ReadOps2Pending;
 
                                psSharedTransferCmd->asDstSyncs[i].sWriteOpsCompleteDevVAddr = psSyncInfo->sWriteOpsCompleteDevVAddr;
                                psSharedTransferCmd->asDstSyncs[i].sReadOpsCompleteDevVAddr = psSyncInfo->sReadOpsCompleteDevVAddr;
+                               psSharedTransferCmd->asDstSyncs[i].sReadOps2CompleteDevVAddr = psSyncInfo->sReadOps2CompleteDevVAddr;
                                i++;
                        }
                }
                PVR_ASSERT(i == ui32RealDstSyncNum);
 
-               
+               /*
+                * We allow source and destination sync objects to be the
+                * same, which is why the read/write pending updates are delayed
+                * until the transfer command has been updated with the current
+                * values from the objects.
+                */
                for (loop = 0; loop < psKick->ui32NumSrcSync; loop++)
                {
                        if (abSrcSyncEnable[loop])
@@ -277,7 +307,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                                {
                                        psSyncInfo = psKick->ahSrcSyncInfo[loop];
 
-                                       PDUMPCOMMENT("Hack src surface write op in transfer cmd\r\n");
+                                       PDUMPCOMMENT("Tweak src surface write op in transfer cmd\r\n");
                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                                        psCCBMemInfo,
                                                        psKick->ui32CCBDumpWOff + (IMG_UINT32)(offsetof(SGXMKIF_TRANSFERCMD_SHARED, asSrcSyncs) + i * sizeof(PVRSRV_DEVICE_SYNC_OBJECT) + offsetof(PVRSRV_DEVICE_SYNC_OBJECT, ui32WriteOpsPendingVal)),
@@ -285,7 +315,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                                                        psKick->ui32PDumpFlags,
                                                        MAKEUNIQUETAG(psCCBMemInfo));
 
-                                       PDUMPCOMMENT("Hack src surface read op in transfer cmd\r\n");
+                                       PDUMPCOMMENT("Tweak src surface read op in transfer cmd\r\n");
                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                                        psCCBMemInfo,
                                                        psKick->ui32CCBDumpWOff + (IMG_UINT32)(offsetof(SGXMKIF_TRANSFERCMD_SHARED, asSrcSyncs) + i * sizeof(PVRSRV_DEVICE_SYNC_OBJECT) + offsetof(PVRSRV_DEVICE_SYNC_OBJECT, ui32ReadOpsPendingVal)),
@@ -301,9 +331,10 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                        {
                                if (abDstSyncEnable[i])
                                {
+                                       IMG_UINT32 ui32PDumpReadOp2 = 0;
                                        psSyncInfo = psKick->ahDstSyncInfo[loop];
 
-                                       PDUMPCOMMENT("Hack dest surface write op in transfer cmd\r\n");
+                                       PDUMPCOMMENT("Tweak dest surface write op in transfer cmd\r\n");
                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                                        psCCBMemInfo,
                                                        psKick->ui32CCBDumpWOff + (IMG_UINT32)(offsetof(SGXMKIF_TRANSFERCMD_SHARED, asDstSyncs) + i * sizeof(PVRSRV_DEVICE_SYNC_OBJECT) + offsetof(PVRSRV_DEVICE_SYNC_OBJECT, ui32WriteOpsPendingVal)),
@@ -311,18 +342,31 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                                                        psKick->ui32PDumpFlags,
                                                        MAKEUNIQUETAG(psCCBMemInfo));
 
-                                       PDUMPCOMMENT("Hack dest surface read op in transfer cmd\r\n");
+                                       PDUMPCOMMENT("Tweak dest surface read op in transfer cmd\r\n");
                                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                                        psCCBMemInfo,
                                                        psKick->ui32CCBDumpWOff + (IMG_UINT32)(offsetof(SGXMKIF_TRANSFERCMD_SHARED, asDstSyncs) + i * sizeof(PVRSRV_DEVICE_SYNC_OBJECT) + offsetof(PVRSRV_DEVICE_SYNC_OBJECT, ui32ReadOpsPendingVal)),
                                                        sizeof(psSyncInfo->psSyncData->ui32LastReadOpDumpVal),
                                                        psKick->ui32PDumpFlags,
                                                        MAKEUNIQUETAG(psCCBMemInfo));
+
+                                       PDUMPCOMMENT("Tweak dest surface read op2 in transfer cmd\r\n");
+                                       PDUMPMEM(&ui32PDumpReadOp2,
+                                                       psCCBMemInfo,
+                                                       psKick->ui32CCBDumpWOff + (IMG_UINT32)(offsetof(SGXMKIF_TRANSFERCMD_SHARED, asDstSyncs) + i * sizeof(PVRSRV_DEVICE_SYNC_OBJECT) + offsetof(PVRSRV_DEVICE_SYNC_OBJECT, ui32ReadOps2PendingVal)),
+                                                       sizeof(ui32PDumpReadOp2),
+                                                       psKick->ui32PDumpFlags,
+                                                       MAKEUNIQUETAG(psCCBMemInfo));
                                        i++;
                                }
                        }
 
-                       
+                       /*
+                        * We allow the first source and destination sync objects to be the
+                        * same, which is why the read/write pending updates are delayed
+                        * until the transfer command has been updated with the current
+                        * values from the objects.
+                        */
                        for (loop = 0; loop < (psKick->ui32NumSrcSync); loop++)
                        {
                                if (abSrcSyncEnable[loop])
@@ -383,7 +427,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
 
        if (eError == PVRSRV_ERROR_RETRY)
        {
-               
+               /* Client will retry, so undo the sync ops pending increment(s) done above. */
                if ((psKick->ui32Flags & SGXMKIF_TQFLAGS_KEEPPENDING) == 0UL)
                {
                        for (loop = 0; loop < psKick->ui32NumSrcSync; loop++)
@@ -418,14 +462,14 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
                        }
                }
 
-               
+               /* Command needed to be synchronised with the TA? */
                if (psKick->hTASyncInfo != IMG_NULL)
                {
                        psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psKick->hTASyncInfo;
                        psSyncInfo->psSyncData->ui32WriteOpsPending--;
                }
 
-               
+               /* Command needed to be synchronised with the 3D? */
                if (psKick->h3DSyncInfo != IMG_NULL)
                {
                        psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psKick->h3DSyncInfo;
@@ -445,7 +489,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmitTransferKM(IMG_HANDLE hDevHandle, PVRSRV_TRANSF
 #if defined(NO_HARDWARE)
        if ((psKick->ui32Flags & SGXMKIF_TQFLAGS_NOSYNCUPDATE) == 0)
        {
-               
+               /* Update sync objects pretending that we have done the job*/
                for (loop = 0; loop < psKick->ui32NumSrcSync; loop++)
                {
                        if (abSrcSyncEnable[loop])
@@ -501,7 +545,11 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
        IMG_HANDLE hDevMemContext = IMG_NULL;
 #if defined(PDUMP)
        IMG_BOOL bPersistentProcess = IMG_FALSE;
-       
+       /*
+        *      For persistent processes, the HW kicks should not go into the
+        *      extended init phase; only keep memory transactions from the
+        *      window system which are necessary to run the client app.
+        */
        {
                PVRSRV_PER_PROCESS_DATA* psPerProc = PVRSRVFindPerProcessData();
                if(psPerProc != IMG_NULL)
@@ -509,7 +557,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                        bPersistentProcess = psPerProc->bPDumpPersistent;
                }
        }
-#endif 
+#endif /* PDUMP */
 #if defined(FIX_HW_BRN_31620)
        hDevMemContext = psKick->hDevMemContext;
 #endif
@@ -519,13 +567,13 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                PVR_DPF((PVR_DBG_ERROR, "SGXSubmit2DKM: Invalid CCB offset"));
                return PVRSRV_ERROR_INVALID_PARAMS;
        }
-       
-       
+       /* override QAC warning about stricter alignment */
+       /* PRQA S 3305 1 */
        ps2DCmd =  CCB_DATA_FROM_OFFSET(SGXMKIF_2DCMD_SHARED, psCCBMemInfo, psKick, ui32SharedCmdCCBOffset);
 
        OSMemSet(ps2DCmd, 0, sizeof(*ps2DCmd));
 
-       
+       /* Command needs to be synchronised with the TA? */
        if (psKick->hTASyncInfo != IMG_NULL)
        {
                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psKick->hTASyncInfo;
@@ -537,7 +585,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                ps2DCmd->sTASyncData.sReadOpsCompleteDevVAddr   = psSyncInfo->sReadOpsCompleteDevVAddr;
        }
 
-       
+       /* Command needs to be synchronised with the 3D? */
        if (psKick->h3DSyncInfo != IMG_NULL)
        {
                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psKick->h3DSyncInfo;
@@ -549,7 +597,12 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                ps2DCmd->s3DSyncData.sReadOpsCompleteDevVAddr = psSyncInfo->sReadOpsCompleteDevVAddr;
        }
 
-       
+       /*
+        * We allow the first source and destination sync objects to be the
+        * same, which is why the read/write pending updates are delayed
+        * until the transfer command has been updated with the current
+        * values from the objects.
+        */
        ps2DCmd->ui32NumSrcSync = psKick->ui32NumSrcSync;
        for (i = 0; i < psKick->ui32NumSrcSync; i++)
        {
@@ -568,12 +621,14 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
 
                ps2DCmd->sDstSyncData.ui32WriteOpsPendingVal = psSyncInfo->psSyncData->ui32WriteOpsPending;
                ps2DCmd->sDstSyncData.ui32ReadOpsPendingVal = psSyncInfo->psSyncData->ui32ReadOpsPending;
+               ps2DCmd->sDstSyncData.ui32ReadOps2PendingVal = psSyncInfo->psSyncData->ui32ReadOps2Pending;
 
                ps2DCmd->sDstSyncData.sWriteOpsCompleteDevVAddr = psSyncInfo->sWriteOpsCompleteDevVAddr;
                ps2DCmd->sDstSyncData.sReadOpsCompleteDevVAddr = psSyncInfo->sReadOpsCompleteDevVAddr;
+               ps2DCmd->sDstSyncData.sReadOps2CompleteDevVAddr = psSyncInfo->sReadOps2CompleteDevVAddr;
        }
 
-       
+       /* Read/Write ops pending updates, delayed from above */
        for (i = 0; i < psKick->ui32NumSrcSync; i++)
        {
                psSyncInfo = psKick->ahSrcSyncInfo[i];
@@ -591,7 +646,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
        || ((psKick->ui32PDumpFlags & PDUMP_FLAGS_CONTINUOUS) != 0))
        &&  (bPersistentProcess == IMG_FALSE) )
        {
-               
+               /* Pdump the command from the per context CCB */
                PDUMPCOMMENT("Shared part of 2D command\r\n");
                PDUMPMEM(ps2DCmd,
                                psCCBMemInfo,
@@ -604,7 +659,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                {
                        psSyncInfo = psKick->ahSrcSyncInfo[i];
 
-                       PDUMPCOMMENT("Hack src surface write op in 2D cmd\r\n");
+                       PDUMPCOMMENT("Tweak src surface write op in 2D cmd\r\n");
                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                        psCCBMemInfo,
                                        psKick->ui32CCBDumpWOff + (IMG_UINT32)offsetof(SGXMKIF_2DCMD_SHARED, sSrcSyncData[i].ui32WriteOpsPendingVal),
@@ -612,7 +667,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                                        psKick->ui32PDumpFlags,
                                        MAKEUNIQUETAG(psCCBMemInfo));
 
-                       PDUMPCOMMENT("Hack src surface read op in 2D cmd\r\n");
+                       PDUMPCOMMENT("Tweak src surface read op in 2D cmd\r\n");
                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                        psCCBMemInfo,
                                        psKick->ui32CCBDumpWOff + (IMG_UINT32)offsetof(SGXMKIF_2DCMD_SHARED, sSrcSyncData[i].ui32ReadOpsPendingVal),
@@ -623,9 +678,10 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
 
                if (psKick->hDstSyncInfo != IMG_NULL)
                {
+                       IMG_UINT32 ui32PDumpReadOp2 = 0;
                        psSyncInfo = psKick->hDstSyncInfo;
 
-                       PDUMPCOMMENT("Hack dest surface write op in 2D cmd\r\n");
+                       PDUMPCOMMENT("Tweak dest surface write op in 2D cmd\r\n");
                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastOpDumpVal,
                                        psCCBMemInfo,
                                        psKick->ui32CCBDumpWOff + (IMG_UINT32)offsetof(SGXMKIF_2DCMD_SHARED, sDstSyncData.ui32WriteOpsPendingVal),
@@ -633,16 +689,23 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                                        psKick->ui32PDumpFlags,
                                        MAKEUNIQUETAG(psCCBMemInfo));
 
-                       PDUMPCOMMENT("Hack dest surface read op in 2D cmd\r\n");
+                       PDUMPCOMMENT("Tweak dest surface read op in 2D cmd\r\n");
                        PDUMPMEM(&psSyncInfo->psSyncData->ui32LastReadOpDumpVal,
                                        psCCBMemInfo,
                                        psKick->ui32CCBDumpWOff + (IMG_UINT32)offsetof(SGXMKIF_2DCMD_SHARED, sDstSyncData.ui32ReadOpsPendingVal),
                                        sizeof(psSyncInfo->psSyncData->ui32LastReadOpDumpVal),
                                        psKick->ui32PDumpFlags,
                                        MAKEUNIQUETAG(psCCBMemInfo));
+                       PDUMPCOMMENT("Tweak dest surface read op2 in 2D cmd\r\n");
+                       PDUMPMEM(&ui32PDumpReadOp2,
+                                       psCCBMemInfo,
+                                       psKick->ui32CCBDumpWOff + (IMG_UINT32)offsetof(SGXMKIF_2DCMD_SHARED, sDstSyncData.ui32ReadOps2PendingVal),
+                                       sizeof(ui32PDumpReadOp2),
+                                       psKick->ui32PDumpFlags,
+                                       MAKEUNIQUETAG(psCCBMemInfo));
                }
 
-               
+               /* Read/Write ops pending updates, delayed from above */
                for (i = 0; i < psKick->ui32NumSrcSync; i++)
                {
                        psSyncInfo = psKick->ahSrcSyncInfo[i];
@@ -663,8 +726,9 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
 
        if (eError == PVRSRV_ERROR_RETRY)
        {
-               
-
+               /* Client will retry, so undo the write ops pending increment
+                  done above.
+                */
 #if defined(PDUMP)
                if (PDumpIsCaptureFrameKM())
                {
@@ -694,7 +758,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                        psSyncInfo->psSyncData->ui32WriteOpsPending--;
                }
 
-               
+               /* Command needed to be synchronised with the TA? */
                if (psKick->hTASyncInfo != IMG_NULL)
                {
                        psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psKick->hTASyncInfo;
@@ -702,7 +766,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
                        psSyncInfo->psSyncData->ui32WriteOpsPending--;
                }
 
-               
+               /* Command needed to be synchronised with the 3D? */
                if (psKick->h3DSyncInfo != IMG_NULL)
                {
                        psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psKick->h3DSyncInfo;
@@ -715,7 +779,7 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
 
 
 #if defined(NO_HARDWARE)
-       
+       /* Update sync objects pretending that we have done the job*/
        for(i = 0; i < psKick->ui32NumSrcSync; i++)
        {
                psSyncInfo = (PVRSRV_KERNEL_SYNC_INFO *)psKick->ahSrcSyncInfo[i];
@@ -746,5 +810,5 @@ IMG_EXPORT PVRSRV_ERROR SGXSubmit2DKM(IMG_HANDLE hDevHandle, PVRSRV_2D_SGX_KICK
 
        return eError;
 }
-#endif 
-#endif 
+#endif /* SGX_FEATURE_2D_HARDWARE */
+#endif /* TRANSFER_QUEUE */
index 1fbca00..bb45433 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device specific utility routines
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Device specific functions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <stddef.h>
 
 #include "ttrace.h"
 
 #ifdef __linux__
-#include <linux/kernel.h>      
-#include <linux/string.h>      
+#include <linux/kernel.h>      // sprintf
+#include <linux/string.h>      // strncpy, strlen
 #else
 #include <stdio.h>
 #endif
 
+IMG_UINT64 ui64KickCount;
+
 
 #if defined(SYS_CUSTOM_POWERDOWN)
 PVRSRV_ERROR SysPowerDownMISR(PVRSRV_DEVICE_NODE       * psDeviceNode, IMG_UINT32 ui32CallerID);
@@ -56,20 +74,38 @@ PVRSRV_ERROR SysPowerDownMISR(PVRSRV_DEVICE_NODE    * psDeviceNode, IMG_UINT32 ui32
 
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXPostActivePowerEvent
+
+ @Description
+
+        post power event functionality (e.g. restart)
+
+ @Input        psDeviceNode : SGX Device Node
+ @Input        ui32CallerID - KERNEL_ID or ISR_ID
+
+ @Return   IMG_VOID :
+
+******************************************************************************/
 static IMG_VOID SGXPostActivePowerEvent(PVRSRV_DEVICE_NODE     * psDeviceNode,
                                                                                IMG_UINT32           ui32CallerID)
 {
        PVRSRV_SGXDEV_INFO      *psDevInfo = psDeviceNode->pvDevice;
        SGXMKIF_HOST_CTL        *psSGXHostCtl = psDevInfo->psSGXHostCtl;
 
-       
+       /* Update the counter for stats. */
        psSGXHostCtl->ui32NumActivePowerEvents++;
 
        if ((psSGXHostCtl->ui32PowerStatus & PVRSRV_USSE_EDM_POWMAN_POWEROFF_RESTART_IMMEDIATE) != 0)
        {
+               PVR_DPF((PVR_DBG_MESSAGE, "SGXPostActivePowerEvent: SGX requests immediate restart"));
                
-
-
+               /*
+                       Events were queued during the active power
+                       request, so SGX will need to be restarted.
+            */
                if (ui32CallerID == ISR_ID)
                {
                        psDeviceNode->bReProcessDeviceCommandComplete = IMG_TRUE;
@@ -82,6 +118,22 @@ static IMG_VOID SGXPostActivePowerEvent(PVRSRV_DEVICE_NODE  * psDeviceNode,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXTestActivePowerEvent
+
+ @Description
+
+ Checks whether the microkernel has generated an active power event. If so,
+       perform the power transition.
+
+ @Input        psDeviceNode : SGX Device Node
+ @Input        ui32CallerID - KERNEL_ID or ISR_ID
+
+ @Return   IMG_VOID :
+
+******************************************************************************/
 IMG_VOID SGXTestActivePowerEvent (PVRSRV_DEVICE_NODE   *psDeviceNode,
                                                                  IMG_UINT32                    ui32CallerID)
 {
@@ -89,38 +141,76 @@ IMG_VOID SGXTestActivePowerEvent (PVRSRV_DEVICE_NODE       *psDeviceNode,
        PVRSRV_SGXDEV_INFO      *psDevInfo = psDeviceNode->pvDevice;
        SGXMKIF_HOST_CTL        *psSGXHostCtl = psDevInfo->psSGXHostCtl;
 
-       if (((psSGXHostCtl->ui32InterruptFlags & PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER) != 0) &&
-               ((psSGXHostCtl->ui32InterruptClearFlags & PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER) == 0))
+#if defined(SYS_SUPPORTS_SGX_IDLE_CALLBACK)
+       if (!psDevInfo->bSGXIdle &&
+               ((psSGXHostCtl->ui32InterruptFlags & PVRSRV_USSE_EDM_INTERRUPT_IDLE) != 0))
        {
-               
+               psDevInfo->bSGXIdle = IMG_TRUE;
+               SysSGXIdleTransition(psDevInfo->bSGXIdle);
+       }
+       else if (psDevInfo->bSGXIdle &&
+                       ((psSGXHostCtl->ui32InterruptFlags & PVRSRV_USSE_EDM_INTERRUPT_IDLE) == 0))
+       {
+               psDevInfo->bSGXIdle = IMG_FALSE;
+               SysSGXIdleTransition(psDevInfo->bSGXIdle);
+       }
+#endif /* SYS_SUPPORTS_SGX_IDLE_CALLBACK */
+
+       /*
+        * Quickly check (without lock) if there is an APM event we should handle.
+        * This check fails most of the time so we don't want to incur lock overhead.
+        * Check the flags in the reverse order that microkernel clears them to prevent
+        * us from seeing an inconsistent state.
+        */
+       if (((psSGXHostCtl->ui32InterruptClearFlags & PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER) == 0) &&
+               ((psSGXHostCtl->ui32InterruptFlags & PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER) != 0))
+       {
+               eError = PVRSRVPowerLock(ui32CallerID, IMG_FALSE);
+               if (eError == PVRSRV_ERROR_RETRY)
+               {
+                       return;
+               }
+               else if (eError != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,"SGXTestActivePowerEvent failed to acquire lock - "
+                    "ui32CallerID:%d eError:%u", ui32CallerID, eError));
+                       return;
+               }
+
+               /*
+                * Check again (with lock) if APM event has been cleared or handled. A race
+                * condition may allow multiple threads to pass the quick check.
+                */
+               if (((psSGXHostCtl->ui32InterruptClearFlags & PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER) != 0) ||
+                       ((psSGXHostCtl->ui32InterruptFlags & PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER) == 0))
+               {
+                       PVRSRVPowerUnlock(ui32CallerID);
+                       return;
+               }
+
+               /* Microkernel is idle and is requesting to be powered down. */
                psSGXHostCtl->ui32InterruptClearFlags |= PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER;
 
-               
+               /* Suspend pdumping. */
                PDUMPSUSPEND();
 
 #if defined(SYS_CUSTOM_POWERDOWN)
-               
-
-
+               /*
+                       Some power down code cannot be executed inside an MISR on
+                       some platforms that use mutexes inside the power code.
+                */
                eError = SysPowerDownMISR(psDeviceNode, ui32CallerID);
 #else
                eError = PVRSRVSetDevicePowerStateKM(psDeviceNode->sDevId.ui32DeviceIndex,
-                                                                                        PVRSRV_DEV_POWER_STATE_OFF,
-                                                                                        ui32CallerID, IMG_FALSE);
+                                                                                        PVRSRV_DEV_POWER_STATE_OFF);
                if (eError == PVRSRV_OK)
                {
                        SGXPostActivePowerEvent(psDeviceNode, ui32CallerID);
                }
 #endif
-               if (eError == PVRSRV_ERROR_RETRY)
-               {
-                       
-
-                       psSGXHostCtl->ui32InterruptClearFlags &= ~PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER;
-                       eError = PVRSRV_OK;
-               }
+               PVRSRVPowerUnlock(ui32CallerID);
 
-               
+               /* Resume pdumping */
                PDUMPRESUME();
        }
 
@@ -131,6 +221,15 @@ IMG_VOID SGXTestActivePowerEvent (PVRSRV_DEVICE_NODE       *psDeviceNode,
 }
 
 
+/******************************************************************************
+ FUNCTION      : SGXAcquireKernelCCBSlot
+
+ PURPOSE       : Attempts to obtain a slot in the Kernel CCB
+
+ PARAMETERS    : psCCB - the CCB
+
+ RETURNS       : Address of space if available, IMG_NULL otherwise
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(SGXAcquireKernelCCBSlot)
 #endif
@@ -146,10 +245,27 @@ static INLINE SGXMKIF_COMMAND * SGXAcquireKernelCCBSlot(PVRSRV_SGX_CCB_INFO *psC
                OSSleepms(1);
        } END_LOOP_UNTIL_TIMEOUT();
 
-       
+       /* Time out on waiting for CCB space */
        return IMG_NULL;
 }
 
+/*!
+******************************************************************************
+
+ @Function     SGXScheduleCCBCommand
+
+ @Description - Submits a CCB command and kicks the ukernel (without
+                               power management)
+
+ @Input psDevInfo - pointer to device info
+ @Input eCmdType - see SGXMKIF_CMD_*
+ @Input psCommandData - kernel CCB command
+ @Input ui32CallerID - KERNEL_ID or ISR_ID
+ @Input ui32PDumpFlags
+
+ @Return ui32Error - success or failure
+
+******************************************************************************/
 PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE  *psDeviceNode,
                                                                   SGXMKIF_CMD_TYPE             eCmdType,
                                                                   SGXMKIF_COMMAND              *psCommandData,
@@ -162,6 +278,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
        PVRSRV_ERROR eError = PVRSRV_OK;
        SGXMKIF_COMMAND *psSGXCommand;
        PVRSRV_SGXDEV_INFO      *psDevInfo = psDeviceNode->pvDevice;
+       SGXMKIF_HOST_CTL        *psSGXHostCtl = psDevInfo->psSGXHostCtl;
 #if defined(FIX_HW_BRN_31620)
        IMG_UINT32 ui32CacheMasks[4];
        IMG_UINT32 i;
@@ -185,7 +302,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
        psMMUContext = psDevInfo->hKernelMMUContext;
        psDeviceNode->pfnMMUGetCacheFlushRange(psMMUContext, &ui32CacheMasks[0]);
 
-       
+       /* Put the apps memory context in the bottom half */
        if (hDevMemContext)
        {
                BM_CONTEXT *psBMContext = (BM_CONTEXT *) hDevMemContext;
@@ -194,7 +311,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
                psDeviceNode->pfnMMUGetCacheFlushRange(psMMUContext, &ui32CacheMasks[2]);
        }
 
-       
+       /* If we have an outstanding flush request then set the cachecontrol bit */
        if (ui32CacheMasks[0] || ui32CacheMasks[1] || ui32CacheMasks[2] || ui32CacheMasks[3])
        {
                psDevInfo->ui32CacheControl |= SGXMKIF_CC_INVAL_BIF_PD;
@@ -202,10 +319,11 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE     *psDeviceNode,
 #endif
 
 #if defined(FIX_HW_BRN_28889)
-       
-
-
-
+       /*
+               If the data cache and bif cache need invalidating there has been a cleanup
+               request. Therefore, we need to send the invalidate seperately and wait
+               for it to complete.
+       */
        if ( (eCmdType != SGXMKIF_CMD_PROCESS_QUEUES) &&
                 ((psDevInfo->ui32CacheControl & SGXMKIF_CC_INVAL_DATA) != 0) &&
                 ((psDevInfo->ui32CacheControl & (SGXMKIF_CC_INVAL_BIF_PT | SGXMKIF_CC_INVAL_BIF_PD)) != 0))
@@ -228,7 +346,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
                        goto Exit;
                }
 
-               
+               /* Wait for the invalidate to happen */
                #if !defined(NO_HARDWARE)
                if(PollForValueKM(&psSGXHostCtl->ui32InvalStatus,
                                                  PVRSRV_USSE_EDM_BIF_INVAL_COMPLETE,
@@ -243,7 +361,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
                #endif
 
                #if defined(PDUMP)
-               
+               /* Pdump the poll as well. */
                PDUMPCOMMENTWITHFLAGS(0, "Host Control - Poll for BIF cache invalidate request to complete");
                PDUMPMEMPOL(psSGXHostCtlMemInfo,
                                        offsetof(SGXMKIF_HOST_CTL, ui32InvalStatus),
@@ -252,7 +370,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
                                        PDUMP_POLL_OPERATOR_EQUAL,
                                        0,
                                        MAKEUNIQUETAG(psSGXHostCtlMemInfo));
-               #endif 
+               #endif /* PDUMP */
 
                psSGXHostCtl->ui32InvalStatus &= ~(PVRSRV_USSE_EDM_BIF_INVAL_COMPLETE);
                PDUMPMEM(IMG_NULL, psSGXHostCtlMemInfo, offsetof(SGXMKIF_HOST_CTL, ui32CleanupStatus), sizeof(IMG_UINT32), 0, MAKEUNIQUETAG(psSGXHostCtlMemInfo));
@@ -267,7 +385,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
                SGXMKIF_COMMAND         sPDECacheCommand = {0};
                IMG_DEV_PHYADDR         sDevPAddr;
 
-               
+               /* Put the kernel info in the top 1/2 of the data */
                psMMUContext = psDevInfo->hKernelMMUContext;
 
                psDeviceNode->pfnMMUGetPDPhysAddr(psMMUContext, &sDevPAddr);
@@ -275,7 +393,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
                sPDECacheCommand.ui32Data[1] = ui32CacheMasks[0];
                sPDECacheCommand.ui32Data[2] = ui32CacheMasks[1];
 
-               
+               /* Put the apps memory context in the bottom half */
                if (hDevMemContext)
                {
                        BM_CONTEXT *psBMContext = (BM_CONTEXT *) hDevMemContext;
@@ -283,13 +401,13 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE     *psDeviceNode,
                        psMMUContext = psBMContext->psMMUContext;
 
                        psDeviceNode->pfnMMUGetPDPhysAddr(psMMUContext, &sDevPAddr);
-                       
+                       /* Or in 1 to the lsb to show we have a valid context */
                        sPDECacheCommand.ui32Data[3] = sDevPAddr.uiAddr | 1;
                        sPDECacheCommand.ui32Data[4] = ui32CacheMasks[2];
                        sPDECacheCommand.ui32Data[5] = ui32CacheMasks[3];
                }
 
-               
+               /* Only do a kick if there is any update */
                if (sPDECacheCommand.ui32Data[1] | sPDECacheCommand.ui32Data[2] | sPDECacheCommand.ui32Data[4] |
                        sPDECacheCommand.ui32Data[5])
                {
@@ -308,7 +426,11 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE      *psDeviceNode,
        }
 #endif
 #if defined(PDUMP)
-       
+       /*
+        *      For persistent processes, the HW kicks should not go into the
+        *      extended init phase; only keep memory transactions from the
+        *      window system which are necessary to run the client app.
+        */
        {
                PVRSRV_PER_PROCESS_DATA* psPerProc = PVRSRVFindPerProcessData();
                if(psPerProc != IMG_NULL)
@@ -316,12 +438,12 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE     *psDeviceNode,
                        bPersistentProcess = psPerProc->bPDumpPersistent;
                }
        }
-#endif 
+#endif /* PDUMP */
        psKernelCCB = psDevInfo->psKernelCCBInfo;
 
        psSGXCommand = SGXAcquireKernelCCBSlot(psKernelCCB);
 
-       
+       /* Wait for CCB space timed out */
        if(!psSGXCommand)
        {
                PVR_DPF((PVR_DBG_ERROR, "SGXScheduleCCBCommand: Wait for CCB space timed out")) ;
@@ -329,18 +451,18 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE     *psDeviceNode,
                goto Exit;
        }
 
-       
+       /* embed cache control word */
        psCommandData->ui32CacheControl = psDevInfo->ui32CacheControl;
 
 #if defined(PDUMP)
-       
+       /* Accumulate any cache invalidates that may have happened */
        psDevInfo->sPDContext.ui32CacheControl |= psDevInfo->ui32CacheControl;
 #endif
 
-       
+       /* and clear it */
        psDevInfo->ui32CacheControl = 0;
 
-       
+       /* Copy command data over */
        *psSGXCommand = *psCommandData;
 
        if (eCmdType >= SGXMKIF_CMD_MAX)
@@ -350,11 +472,13 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE     *psDeviceNode,
                goto Exit;
        }
 
-       if ((eCmdType == SGXMKIF_CMD_TA) && bLastInScene)
+       if (eCmdType == SGXMKIF_CMD_2D ||
+               eCmdType == SGXMKIF_CMD_TRANSFER ||
+               ((eCmdType == SGXMKIF_CMD_TA) && bLastInScene))
        {
                SYS_DATA *psSysData;
 
-               
+               /* CPU cache clean control */
                SysAcquireData(&psSysData);
 
                if(psSysData->ePendingCacheOpType == PVRSRV_MISC_INFO_CPUCACHEOP_FLUSH)
@@ -366,18 +490,18 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE     *psDeviceNode,
                        OSCleanCPUCacheKM();
                }
 
-               
+               /* Clear the pending op */
                psSysData->ePendingCacheOpType = PVRSRV_MISC_INFO_CPUCACHEOP_NONE;
        }
 
        PVR_ASSERT(eCmdType < SGXMKIF_CMD_MAX);
-       psSGXCommand->ui32ServiceAddress = psDevInfo->aui32HostKickAddr[eCmdType];       
+       psSGXCommand->ui32ServiceAddress = psDevInfo->aui32HostKickAddr[eCmdType];      /* PRQA S 3689 */ /* misuse of enums for bounds checking */
 
 #if defined(PDUMP)
        if ((ui32CallerID != ISR_ID) && (bPDumpIsSuspended == IMG_FALSE) &&
                (bPersistentProcess == IMG_FALSE) )
        {
-               
+               /* Poll for space in the CCB. */
                PDUMPCOMMENTWITHFLAGS(ui32PDumpFlags, "Poll for space in the Kernel CCB\r\n");
                PDUMPMEMPOL(psKernelCCB->psCCBCtlMemInfo,
                                        offsetof(PVRSRV_SGX_CCB_CTL, ui32ReadOffset),
@@ -397,7 +521,7 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
                                        ui32PDumpFlags,
                                        MAKEUNIQUETAG(psKernelCCB->psCCBMemInfo));
 
-               
+               /* Overwrite cache control with pdump shadow */
                PDUMPMEM(&psDevInfo->sPDContext.ui32CacheControl,
                                        psKernelCCB->psCCBMemInfo,
                                        psKernelCCB->ui32CCBDumpWOff * sizeof(SGXMKIF_COMMAND) +
@@ -409,14 +533,14 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE     *psDeviceNode,
                if (PDumpIsCaptureFrameKM()
                || ((ui32PDumpFlags & PDUMP_FLAGS_CONTINUOUS) != 0))
                {
-                       
+                       /* Clear cache invalidate shadow */
                        psDevInfo->sPDContext.ui32CacheControl = 0;
                }
        }
 #endif
 
 #if defined(FIX_HW_BRN_26620) && defined(SGX_FEATURE_SYSTEM_CACHE) && !defined(SGX_BYPASS_SYSTEM_CACHE)
-       
+       /* Make sure the previous command has been read before send the next one */
        eError = PollForValueKM (psKernelCCB->pui32ReadOffset,
                                                                *psKernelCCB->pui32WriteOffset,
                                                                0xFF,
@@ -431,8 +555,9 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE       *psDeviceNode,
        }
 #endif
 
-       
-
+       /*
+               Increment the write offset
+       */
        *psKernelCCB->pui32WriteOffset = (*psKernelCCB->pui32WriteOffset + 1) & 255;
 
 #if defined(PDUMP)
@@ -482,9 +607,16 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE      *psDeviceNode,
 
        *psDevInfo->pui32KernelCCBEventKicker = (*psDevInfo->pui32KernelCCBEventKicker + 1) & 0xFF;
 
+       /*
+        * New command submission is considered a proper handling of any pending APM
+        * event, so mark it as handled to prevent other host threads from taking
+        * action.
+        */
+       psSGXHostCtl->ui32InterruptClearFlags |= PVRSRV_USSE_EDM_INTERRUPT_ACTIVE_POWER;
+
        OSWriteMemoryBarrier();
 
-       
+       /* Order is importent for post processor! */
        PVR_TTRACE_UI32(PVRSRV_TRACE_GROUP_MKSYNC, PVRSRV_TRACE_CLASS_NONE,
                        MKSYNC_TOKEN_KERNEL_CCB_OFFSET, *psKernelCCB->pui32WriteOffset);
        PVR_TTRACE_UI32(PVRSRV_TRACE_GROUP_MKSYNC, PVRSRV_TRACE_CLASS_NONE,
@@ -506,15 +638,32 @@ PVRSRV_ERROR SGXScheduleCCBCommand(PVRSRV_DEVICE_NODE     *psDeviceNode,
        OSMemoryBarrier();
 
 #if defined(NO_HARDWARE)
-       
+       /* Increment read offset */
        *psKernelCCB->pui32ReadOffset = (*psKernelCCB->pui32ReadOffset + 1) & 255;
 #endif
 
+       ui64KickCount++;
 Exit:
        return eError;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXScheduleCCBCommandKM
+
+ @Description - Submits a CCB command and kicks the ukernel
+
+ @Input psDeviceNode - pointer to SGX device node
+ @Input eCmdType - see SGXMKIF_CMD_*
+ @Input psCommandData - kernel CCB command
+ @Input ui32CallerID - KERNEL_ID or ISR_ID
+ @Input ui32PDumpFlags
+
+ @Return ui32Error - success or failure
+
+******************************************************************************/
 PVRSRV_ERROR SGXScheduleCCBCommandKM(PVRSRV_DEVICE_NODE                *psDeviceNode,
                                                                         SGXMKIF_CMD_TYPE               eCmdType,
                                                                         SGXMKIF_COMMAND                *psCommandData,
@@ -523,16 +672,47 @@ PVRSRV_ERROR SGXScheduleCCBCommandKM(PVRSRV_DEVICE_NODE           *psDeviceNode,
                                                                         IMG_HANDLE                             hDevMemContext,
                                                                         IMG_BOOL                               bLastInScene)
 {
-       PVRSRV_ERROR            eError;
+       PVRSRV_ERROR    eError;
 
-       
+       eError = PVRSRVPowerLock(ui32CallerID, IMG_FALSE);
+       if (eError == PVRSRV_ERROR_RETRY)
+       {
+               if (ui32CallerID == ISR_ID)
+               {
+                       SYS_DATA *psSysData;
+                       
+                       /*
+                               ISR failed to acquire lock so it must be held by a kernel thread.
+                               Bring up and kick SGX if necessary when the lock is available.
+                       */
+                       psDeviceNode->bReProcessDeviceCommandComplete = IMG_TRUE;
+                       eError = PVRSRV_OK;
+
+                       SysAcquireData(&psSysData);
+                       OSScheduleMISR(psSysData);
+               }
+               else
+               {
+                       /*
+                               Return to srvclient for retry.
+                       */
+               }
+
+               return eError;
+       }
+       else if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"SGXScheduleCCBCommandKM failed to acquire lock - "
+                               "ui32CallerID:%d eError:%u", ui32CallerID, eError));
+               return eError;
+       }
+
+       /* Note that a power-up has been dumped in the init phase. */
        PDUMPSUSPEND();
 
-       
+       /* Ensure that SGX is powered up before kicking the ukernel. */
        eError = PVRSRVSetDevicePowerStateKM(psDeviceNode->sDevId.ui32DeviceIndex,
-                                                                                PVRSRV_DEV_POWER_STATE_ON,
-                                                                                ui32CallerID,
-                                                                                IMG_TRUE);
+                                                                                PVRSRV_DEV_POWER_STATE_ON);
 
        PDUMPRESUME();
 
@@ -542,33 +722,8 @@ PVRSRV_ERROR SGXScheduleCCBCommandKM(PVRSRV_DEVICE_NODE            *psDeviceNode,
        }
        else
        {
-               if (eError == PVRSRV_ERROR_RETRY)
-               {
-                       if (ui32CallerID == ISR_ID)
-                       {
-                               SYS_DATA *psSysData;
-                               
-                               
-
-
-                               psDeviceNode->bReProcessDeviceCommandComplete = IMG_TRUE;
-                               eError = PVRSRV_OK;
-
-                               SysAcquireData(&psSysData);
-                               OSScheduleMISR(psSysData);
-                       }
-                       else
-                       {
-                               
-
-                       }
-               }
-               else
-               {
-                       PVR_DPF((PVR_DBG_ERROR,"SGXScheduleCCBCommandKM failed to acquire lock - "
-                                        "ui32CallerID:%d eError:%u", ui32CallerID, eError));
-               }
-
+               PVR_DPF((PVR_DBG_ERROR,"SGXScheduleCCBCommandKM failed to acquire lock - "
+                                "ui32CallerID:%d eError:%u", ui32CallerID, eError));
                return eError;
        }
 
@@ -579,6 +734,16 @@ PVRSRV_ERROR SGXScheduleCCBCommandKM(PVRSRV_DEVICE_NODE            *psDeviceNode,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXScheduleProcessQueuesKM
+
+ @Description - Software command complete handler
+
+ @Input psDeviceNode - SGX device node
+
+******************************************************************************/
 PVRSRV_ERROR SGXScheduleProcessQueuesKM(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        PVRSRV_ERROR            eError;
@@ -590,7 +755,7 @@ PVRSRV_ERROR SGXScheduleProcessQueuesKM(PVRSRV_DEVICE_NODE *psDeviceNode)
        ui32PowerStatus = psHostCtl->ui32PowerStatus;
        if ((ui32PowerStatus & PVRSRV_USSE_EDM_POWMAN_NO_WORK) != 0)
        {
-               
+               /* The ukernel has no work to do so don't waste power. */
                return PVRSRV_OK;
        }
 
@@ -605,11 +770,41 @@ PVRSRV_ERROR SGXScheduleProcessQueuesKM(PVRSRV_DEVICE_NODE *psDeviceNode)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SGXIsDevicePowered
+
+ @Description
+
+       Whether the device is powered, for the purposes of lockup detection.
+
+ @Input psDeviceNode - pointer to device node
+
+ @Return   IMG_BOOL  : Whether device is powered
+
+******************************************************************************/
 IMG_BOOL SGXIsDevicePowered(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        return PVRSRVIsDevicePowered(psDeviceNode->sDevId.ui32DeviceIndex);
 }
 
+/*!
+*******************************************************************************
+
+ @Function     SGXGetInternalDevInfoKM
+
+ @Description
+       Gets device information that is not intended to be passed
+       on beyond the srvclient libs.
+
+ @Input hDevCookie
+
+ @Output psSGXInternalDevInfo
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR SGXGetInternalDevInfoKM(IMG_HANDLE hDevCookie,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -623,7 +818,7 @@ PVRSRV_ERROR SGXGetInternalDevInfoKM(IMG_HANDLE hDevCookie,
        psSGXInternalDevInfo->ui32Flags = psDevInfo->ui32Flags;
        psSGXInternalDevInfo->bForcePTOff = (IMG_BOOL)psDevInfo->bForcePTOff;
 
-       
+       /* This should be patched up by OS bridge code */
        psSGXInternalDevInfo->hHostCtlKernelMemInfoHandle =
                (IMG_HANDLE)psDevInfo->psKernelSGXHostCtlMemInfo;
 
@@ -631,6 +826,19 @@ PVRSRV_ERROR SGXGetInternalDevInfoKM(IMG_HANDLE hDevCookie,
 }
 
 
+/*****************************************************************************
+ FUNCTION      : SGXCleanupRequest
+
+ PURPOSE       : Wait for the microkernel to clean up its references to either a
+                               render context or render target.
+
+ PARAMETERS    :       psDeviceNode - SGX device node
+                               psHWDataDevVAddr - Device Address of the resource
+                               ui32CleanupType - PVRSRV_CLEANUPCMD_*
+                               bForceCleanup - Skips sync polling
+
+ RETURNS       : error status
+*****************************************************************************/
 PVRSRV_ERROR SGXCleanupRequest(PVRSRV_DEVICE_NODE *psDeviceNode,
                                                           IMG_DEV_VIRTADDR   *psHWDataDevVAddr,
                                                           IMG_UINT32          ui32CleanupType,
@@ -654,11 +862,12 @@ PVRSRV_ERROR SGXCleanupRequest(PVRSRV_DEVICE_NODE *psDeviceNode,
                if (eError != PVRSRV_OK)
                {
                                PVR_DPF((PVR_DBG_ERROR,"SGXCleanupRequest: Failed to submit clean-up command"));
+                               SGXDumpDebugInfo(psDevInfo, IMG_FALSE);
                                PVR_DBG_BREAK;
                                return eError;
                }
                
-               
+               /* Wait for the uKernel process the cleanup request */
                #if !defined(NO_HARDWARE)
                if(PollForValueKM(&psHostCtl->ui32CleanupStatus,
                                                  PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE,
@@ -669,38 +878,59 @@ PVRSRV_ERROR SGXCleanupRequest(PVRSRV_DEVICE_NODE *psDeviceNode,
                {
                        PVR_DPF((PVR_DBG_ERROR,"SGXCleanupRequest: Wait for uKernel to clean up (%u) failed", ui32CleanupType));
                        eError = PVRSRV_ERROR_TIMEOUT;
+                       SGXDumpDebugInfo(psDevInfo, IMG_FALSE);
                        PVR_DBG_BREAK;
                }
                #endif
        
                #if defined(PDUMP)
-               
+               /*
+                       Pdump the poll as well.
+                       Note:
+                       We don't expect the cleanup to report busy as the client should have
+                       ensured the the resource has been finished with before requesting
+                       it's cleanup. This isn't true of the abnormal termination case but
+                       we don't expect to PDump that. Unless/until PDump has flow control
+                       there isn't anything else we can do.
+               */
                PDUMPCOMMENTWITHFLAGS(0, "Host Control - Poll for clean-up request to complete");
                PDUMPMEMPOL(psHostCtlMemInfo,
                                        offsetof(SGXMKIF_HOST_CTL, ui32CleanupStatus),
-                                       PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE,
-                                       PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE,
+                                       PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE | PVRSRV_USSE_EDM_CLEANUPCMD_DONE,
+                                       PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE | PVRSRV_USSE_EDM_CLEANUPCMD_DONE,
                                        PDUMP_POLL_OPERATOR_EQUAL,
                                        0,
                                        MAKEUNIQUETAG(psHostCtlMemInfo));
-               #endif 
+               #endif /* PDUMP */
        
                if (eError != PVRSRV_OK)
                {
                        return eError;
                }
        }
+
+       if (psHostCtl->ui32CleanupStatus & PVRSRV_USSE_EDM_CLEANUPCMD_BUSY)
+       {
+               /* Only one flag should be set */
+               PVR_ASSERT((psHostCtl->ui32CleanupStatus & PVRSRV_USSE_EDM_CLEANUPCMD_DONE) == 0);
+               eError = PVRSRV_ERROR_RETRY;
+               psHostCtl->ui32CleanupStatus &= ~(PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE | PVRSRV_USSE_EDM_CLEANUPCMD_BUSY);
+       }
+       else
+       {
+               eError = PVRSRV_OK;
+               psHostCtl->ui32CleanupStatus &= ~(PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE | PVRSRV_USSE_EDM_CLEANUPCMD_DONE);
+       }
        
-       psHostCtl->ui32CleanupStatus &= ~(PVRSRV_USSE_EDM_CLEANUPCMD_COMPLETE);
        PDUMPMEM(IMG_NULL, psHostCtlMemInfo, offsetof(SGXMKIF_HOST_CTL, ui32CleanupStatus), sizeof(IMG_UINT32), 0, MAKEUNIQUETAG(psHostCtlMemInfo));
 
-       
+       /* Request the cache invalidate */
 #if defined(SGX_FEATURE_SYSTEM_CACHE)
        psDevInfo->ui32CacheControl |= (SGXMKIF_CC_INVAL_BIF_SL | SGXMKIF_CC_INVAL_DATA);
 #else
        psDevInfo->ui32CacheControl |= SGXMKIF_CC_INVAL_DATA;
 #endif
-       return PVRSRV_OK;
+       return eError;
 }
 
 
@@ -710,6 +940,8 @@ typedef struct _SGX_HW_RENDER_CONTEXT_CLEANUP_
     PVRSRV_KERNEL_MEM_INFO *psHWRenderContextMemInfo;
     IMG_HANDLE hBlockAlloc;
        PRESMAN_ITEM psResItem;
+       IMG_BOOL bCleanupTimerRunning;
+       IMG_PVOID pvTimeData;
 } SGX_HW_RENDER_CONTEXT_CLEANUP;
 
 
@@ -727,16 +959,44 @@ static PVRSRV_ERROR SGXCleanupHWRenderContextCallback(IMG_PVOID           pvParam,
                                          PVRSRV_CLEANUPCMD_RC,
                                          bForceCleanup);
 
-    
-    PVRSRVFreeDeviceMemKM(psCleanup->psDeviceNode,
-            psCleanup->psHWRenderContextMemInfo);
+       if (eError == PVRSRV_ERROR_RETRY)
+       {
+               if (!psCleanup->bCleanupTimerRunning)
+               {
+                       OSTimeCreateWithUSOffset(&psCleanup->pvTimeData, MAX_CLEANUP_TIME_US);
+                       psCleanup->bCleanupTimerRunning = IMG_TRUE;
+               }
+               else
+               {
+                       if (OSTimeHasTimePassed(psCleanup->pvTimeData))
+                       {
+                               eError = PVRSRV_ERROR_TIMEOUT_POLLING_FOR_VALUE;
+                               psCleanup->bCleanupTimerRunning = IMG_FALSE;
+                               OSTimeDestroy(psCleanup->pvTimeData);
+                       }
+               }
+       }
+       else
+       {
+               if (psCleanup->bCleanupTimerRunning)
+               {
+                       OSTimeDestroy(psCleanup->pvTimeData);
+               }
+       }
 
-    
-       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
-                         sizeof(SGX_HW_RENDER_CONTEXT_CLEANUP),
-                         psCleanup,
-                         psCleanup->hBlockAlloc);
+       if (eError != PVRSRV_ERROR_RETRY)
+       {
+           /* Free the Device Mem allocated */
+           PVRSRVFreeDeviceMemKM(psCleanup->psDeviceNode,
+                   psCleanup->psHWRenderContextMemInfo);
        
+           /* Finally, free the cleanup structure itself */
+               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                 sizeof(SGX_HW_RENDER_CONTEXT_CLEANUP),
+                                 psCleanup,
+                                 psCleanup->hBlockAlloc);
+               /*not nulling pointer, copy on stack*/
+       }
 
        return eError;
 }
@@ -747,6 +1007,8 @@ typedef struct _SGX_HW_TRANSFER_CONTEXT_CLEANUP_
     PVRSRV_KERNEL_MEM_INFO *psHWTransferContextMemInfo;
        IMG_HANDLE hBlockAlloc;
        PRESMAN_ITEM psResItem;
+       IMG_BOOL bCleanupTimerRunning;
+       IMG_PVOID pvTimeData;
 } SGX_HW_TRANSFER_CONTEXT_CLEANUP;
 
 
@@ -764,16 +1026,44 @@ static PVRSRV_ERROR SGXCleanupHWTransferContextCallback(IMG_PVOID        pvParam,
                                          PVRSRV_CLEANUPCMD_TC,
                                          bForceCleanup);
 
-    
-    PVRSRVFreeDeviceMemKM(psCleanup->psDeviceNode,
-            psCleanup->psHWTransferContextMemInfo);
+       if (eError == PVRSRV_ERROR_RETRY)
+       {
+               if (!psCleanup->bCleanupTimerRunning)
+               {
+                       OSTimeCreateWithUSOffset(&psCleanup->pvTimeData, MAX_CLEANUP_TIME_US);
+                       psCleanup->bCleanupTimerRunning = IMG_TRUE;
+               }
+               else
+               {
+                       if (OSTimeHasTimePassed(psCleanup->pvTimeData))
+                       {
+                               eError = PVRSRV_ERROR_TIMEOUT_POLLING_FOR_VALUE;
+                               psCleanup->bCleanupTimerRunning = IMG_FALSE;
+                               OSTimeDestroy(psCleanup->pvTimeData);
+                       }
+               }
+       }
+       else
+       {
+               if (psCleanup->bCleanupTimerRunning)
+               {
+                       OSTimeDestroy(psCleanup->pvTimeData);
+               }
+       }
 
-    
-       OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
-                         sizeof(SGX_HW_TRANSFER_CONTEXT_CLEANUP),
-                         psCleanup,
-                         psCleanup->hBlockAlloc);
+       if (eError != PVRSRV_ERROR_RETRY)
+       {
+           /* Free the Device Mem allocated */
+           PVRSRVFreeDeviceMemKM(psCleanup->psDeviceNode,
+                   psCleanup->psHWTransferContextMemInfo);
        
+           /* Finally, free the cleanup structure itself */
+               OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                 sizeof(SGX_HW_TRANSFER_CONTEXT_CLEANUP),
+                                 psCleanup,
+                                 psCleanup->hBlockAlloc);
+               /*not nulling pointer, copy on stack*/
+       }
 
        return eError;
 }
@@ -824,6 +1114,9 @@ IMG_HANDLE SGXRegisterHWRenderContextKM(IMG_HANDLE                         hDeviceNode,
                                  | PVRSRV_MEM_CACHE_CONSISTENT,
                                ui32HWRenderContextSize,
                                32,
+                               IMG_NULL,
+                               0,
+                               0,0,0,IMG_NULL, /* No sparse mapping data */
                                &psCleanup->psHWRenderContextMemInfo,
                                "HW Render Context");
 
@@ -844,10 +1137,10 @@ IMG_HANDLE SGXRegisterHWRenderContextKM(IMG_HANDLE                               hDeviceNode,
                goto exit2;
        }
 
-    
+    /* Pass the DevVAddr of the new context back up through the bridge */
     psHWRenderContextDevVAddr->uiAddr = psCleanup->psHWRenderContextMemInfo->sDevVAddr.uiAddr;
 
-    
+    /* Retrieve the PDDevPAddr */
     eError = PVRSRVLookupHandle(psPerProc->psHandleBase, 
                            &hDevMemContextInt,
                            hDevMemContext,
@@ -862,11 +1155,12 @@ IMG_HANDLE SGXRegisterHWRenderContextKM(IMG_HANDLE                               hDeviceNode,
     psMMUContext = BM_GetMMUContextFromMemContext(hDevMemContextInt);
     sPDDevPAddr = psDeviceNode->pfnMMUGetPDDevPAddr(psMMUContext);
 
-    
-
-
-
-
+    /* 
+       patch-in the Page-Directory Device-Physical address. Note that this is
+       copied-in one byte at a time, as we have no guarantee that the usermode-
+       provided ui32OffsetToPDDevPAddr is a validly-aligned address for the
+       current CPU architecture.
+     */
     pSrc = (IMG_UINT8 *)&sPDDevPAddr;
     pDst = (IMG_UINT8 *)psCleanup->psHWRenderContextMemInfo->pvLinAddrKM;
     pDst += ui32OffsetToPDDevPAddr;
@@ -877,7 +1171,7 @@ IMG_HANDLE SGXRegisterHWRenderContextKM(IMG_HANDLE                         hDeviceNode,
     }
 
 #if defined(PDUMP)
-    
+    /* PDUMP the HW context */
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS, "HW Render context struct");
 
        PDUMPMEM(
@@ -888,7 +1182,7 @@ IMG_HANDLE SGXRegisterHWRenderContextKM(IMG_HANDLE                         hDeviceNode,
         PDUMP_FLAGS_CONTINUOUS, 
         MAKEUNIQUETAG(psCleanup->psHWRenderContextMemInfo));
 
-    
+    /* PDUMP the PDDevPAddr */
        PDUMPCOMMENT("Page directory address in HW render context");
     PDUMPPDDEVPADDR(
             psCleanup->psHWRenderContextMemInfo,
@@ -900,6 +1194,7 @@ IMG_HANDLE SGXRegisterHWRenderContextKM(IMG_HANDLE                         hDeviceNode,
 
        psCleanup->hBlockAlloc = hBlockAlloc;
        psCleanup->psDeviceNode = psDeviceNode;
+       psCleanup->bCleanupTimerRunning = IMG_FALSE;
 
        psResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                  RESMAN_TYPE_HW_RENDER_CONTEXT,
@@ -917,6 +1212,7 @@ IMG_HANDLE SGXRegisterHWRenderContextKM(IMG_HANDLE                         hDeviceNode,
 
        return (IMG_HANDLE)psCleanup;
 
+/* Error exit paths */
 exit2:
         PVRSRVFreeDeviceMemKM(hDeviceNode,
                            psCleanup->psHWRenderContextMemInfo);
@@ -925,7 +1221,7 @@ exit1:
               sizeof(SGX_HW_RENDER_CONTEXT_CLEANUP),
               psCleanup,
               psCleanup->hBlockAlloc);
-    
+    /*not nulling pointer, out of scope*/
 exit0:
     return IMG_NULL;
 }
@@ -998,6 +1294,9 @@ IMG_HANDLE SGXRegisterHWTransferContextKM(IMG_HANDLE                               hDeviceNode,
                                  | PVRSRV_MEM_CACHE_CONSISTENT,
                                ui32HWTransferContextSize,
                                32,
+                               IMG_NULL,
+                               0,
+                               0,0,0,IMG_NULL, /* No sparse mapping data */
                                &psCleanup->psHWTransferContextMemInfo,
                                "HW Render Context");
 
@@ -1018,10 +1317,10 @@ IMG_HANDLE SGXRegisterHWTransferContextKM(IMG_HANDLE                            hDeviceNode,
                goto exit2;
        }
 
-    
+    /* Pass the DevVAddr of the new context back up through the bridge */
     psHWTransferContextDevVAddr->uiAddr = psCleanup->psHWTransferContextMemInfo->sDevVAddr.uiAddr;
 
-    
+    /* Retrieve the PDDevPAddr */
     eError = PVRSRVLookupHandle(psPerProc->psHandleBase, 
                            &hDevMemContextInt,
                            hDevMemContext,
@@ -1036,11 +1335,12 @@ IMG_HANDLE SGXRegisterHWTransferContextKM(IMG_HANDLE                            hDeviceNode,
     psMMUContext = BM_GetMMUContextFromMemContext(hDevMemContextInt);
     sPDDevPAddr = psDeviceNode->pfnMMUGetPDDevPAddr(psMMUContext);
 
-    
-
-
-
-
+    /* 
+       patch-in the Page-Directory Device-Physical address. Note that this is
+       copied-in one byte at a time, as we have no guarantee that the usermode-
+       provided ui32OffsetToPDDevPAddr is a validly-aligned address for the
+       current CPU architecture.
+     */
     pSrc = (IMG_UINT8 *)&sPDDevPAddr;
     pDst = (IMG_UINT8 *)psCleanup->psHWTransferContextMemInfo->pvLinAddrKM;
     pDst += ui32OffsetToPDDevPAddr;
@@ -1051,7 +1351,7 @@ IMG_HANDLE SGXRegisterHWTransferContextKM(IMG_HANDLE                              hDeviceNode,
     }
 
 #if defined(PDUMP)
-    
+    /* PDUMP the HW Transfer Context */
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS, "HW Transfer context struct");
 
        PDUMPMEM(
@@ -1062,7 +1362,7 @@ IMG_HANDLE SGXRegisterHWTransferContextKM(IMG_HANDLE                              hDeviceNode,
         PDUMP_FLAGS_CONTINUOUS, 
         MAKEUNIQUETAG(psCleanup->psHWTransferContextMemInfo));
 
-    
+    /* PDUMP the PDDevPAddr */
        PDUMPCOMMENT("Page directory address in HW transfer context");
 
     PDUMPPDDEVPADDR(
@@ -1075,6 +1375,7 @@ IMG_HANDLE SGXRegisterHWTransferContextKM(IMG_HANDLE                              hDeviceNode,
 
        psCleanup->hBlockAlloc = hBlockAlloc;
        psCleanup->psDeviceNode = psDeviceNode;
+       psCleanup->bCleanupTimerRunning = IMG_FALSE;
 
        psResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                  RESMAN_TYPE_HW_TRANSFER_CONTEXT,
@@ -1092,6 +1393,7 @@ IMG_HANDLE SGXRegisterHWTransferContextKM(IMG_HANDLE                              hDeviceNode,
 
        return (IMG_HANDLE)psCleanup;
 
+/* Error exit paths */
 exit2:
     PVRSRVFreeDeviceMemKM(hDeviceNode,
             psCleanup->psHWTransferContextMemInfo);
@@ -1100,7 +1402,7 @@ exit1:
               sizeof(SGX_HW_TRANSFER_CONTEXT_CLEANUP),
               psCleanup,
               psCleanup->hBlockAlloc);
-    
+    /*not nulling pointer, out of scope*/
 
 exit0:
     return IMG_NULL;
@@ -1154,9 +1456,10 @@ PVRSRV_ERROR SGXSetTransferContextPriorityKM(
             return PVRSRV_ERROR_INVALID_PARAMS;
         }
 
-        
-
-
+        /*
+           cannot be sure that offset (passed from user-land) is safe to deref
+           as a word-ptr on current CPU arch: copy one byte at a time.
+         */
         pDst = (IMG_UINT8 *)psCleanup->psHWTransferContextMemInfo->pvLinAddrKM;
         pDst += ui32OffsetOfPriorityField;
         pSrc = (IMG_UINT8 *)&ui32Priority;
@@ -1195,9 +1498,10 @@ PVRSRV_ERROR SGXSetRenderContextPriorityKM(
             return PVRSRV_ERROR_INVALID_PARAMS;
         }
 
-        
-
-
+        /*
+           cannot be sure that offset (passed from user-land) is safe to deref
+           as a word-ptr on current CPU arch: copy one byte at a time.
+         */
         pDst = (IMG_UINT8 *)psCleanup->psHWRenderContextMemInfo->pvLinAddrKM;
         pDst += ui32OffsetOfPriorityField;
 
@@ -1218,6 +1522,8 @@ typedef struct _SGX_HW_2D_CONTEXT_CLEANUP_
        PVRSRV_KERNEL_MEM_INFO *psHW2DContextMemInfo;
        IMG_HANDLE hBlockAlloc;
        PRESMAN_ITEM psResItem;
+       IMG_BOOL bCleanupTimerRunning;
+       IMG_PVOID pvTimeData;
 } SGX_HW_2D_CONTEXT_CLEANUP;
 
 static PVRSRV_ERROR SGXCleanupHW2DContextCallback(IMG_PVOID  pvParam,
@@ -1229,23 +1535,50 @@ static PVRSRV_ERROR SGXCleanupHW2DContextCallback(IMG_PVOID  pvParam,
 
        PVR_UNREFERENCED_PARAMETER(ui32Param);
 
-    
+    /* First, ensure the context is no longer being utilised */
     eError = SGXCleanupRequest(psCleanup->psDeviceNode,
                                          &psCleanup->psHW2DContextMemInfo->sDevVAddr,
                                          PVRSRV_CLEANUPCMD_2DC,
                                          bForceCleanup);
 
-    
-    PVRSRVFreeDeviceMemKM(psCleanup->psDeviceNode,
-            psCleanup->psHW2DContextMemInfo);
-
-    
-    OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
-                         sizeof(SGX_HW_2D_CONTEXT_CLEANUP),
-                         psCleanup,
-                         psCleanup->hBlockAlloc);
-                  
+       if (eError == PVRSRV_ERROR_RETRY)
+       {
+               if (!psCleanup->bCleanupTimerRunning)
+               {
+                       OSTimeCreateWithUSOffset(&psCleanup->pvTimeData, MAX_CLEANUP_TIME_US);
+                       psCleanup->bCleanupTimerRunning = IMG_TRUE;
+               }
+               else
+               {
+                       if (OSTimeHasTimePassed(psCleanup->pvTimeData))
+                       {
+                               eError = PVRSRV_ERROR_TIMEOUT_POLLING_FOR_VALUE;
+                               psCleanup->bCleanupTimerRunning = IMG_FALSE;
+                               OSTimeDestroy(psCleanup->pvTimeData);
+                       }
+               }
+       }
+       else
+       {
+               if (psCleanup->bCleanupTimerRunning)
+               {
+                       OSTimeDestroy(psCleanup->pvTimeData);
+               }
+       }
 
+       if (eError != PVRSRV_ERROR_RETRY)
+       {
+           /* Free the Device Mem allocated */
+           PVRSRVFreeDeviceMemKM(psCleanup->psDeviceNode,
+                   psCleanup->psHW2DContextMemInfo);
+       
+           /* Finally, free the cleanup structure itself */
+           OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP,
+                                 sizeof(SGX_HW_2D_CONTEXT_CLEANUP),
+                                 psCleanup,
+                                 psCleanup->hBlockAlloc);
+                         /*not nulling pointer, copy on stack*/
+       }
        return eError;
 }
 
@@ -1294,6 +1627,9 @@ IMG_HANDLE SGXRegisterHW2DContextKM(IMG_HANDLE                            hDeviceNode,
                                  | PVRSRV_MEM_CACHE_CONSISTENT,
                                ui32HW2DContextSize,
                                32,
+                               IMG_NULL,
+                               0,
+                               0,0,0,IMG_NULL, /* No sparse mapping data */
                                &psCleanup->psHW2DContextMemInfo,
                                "HW 2D Context");
 
@@ -1313,10 +1649,10 @@ IMG_HANDLE SGXRegisterHW2DContextKM(IMG_HANDLE                          hDeviceNode,
                goto exit2;
        }
  
-    
+    /* Pass the DevVAddr of the new context back up through the bridge */
     psHW2DContextDevVAddr->uiAddr = psCleanup->psHW2DContextMemInfo->sDevVAddr.uiAddr;
 
-    
+    /* Retrieve the PDDevPAddr */
     eError = PVRSRVLookupHandle(psPerProc->psHandleBase, 
                            &hDevMemContextInt,
                            hDevMemContext,
@@ -1331,11 +1667,12 @@ IMG_HANDLE SGXRegisterHW2DContextKM(IMG_HANDLE                          hDeviceNode,
     psMMUContext = BM_GetMMUContextFromMemContext(hDevMemContextInt);
     sPDDevPAddr = psDeviceNode->pfnMMUGetPDDevPAddr(psMMUContext);
 
-    
-
-
-
-
+    /* 
+       patch-in the Page-Directory Device-Physical address. Note that this is
+       copied-in one byte at a time, as we have no guarantee that the usermode-
+       provided ui32OffsetToPDDevPAddr is a validly-aligned address for the
+       current CPU architecture.
+     */
     pSrc = (IMG_UINT8 *)&sPDDevPAddr;
     pDst = (IMG_UINT8 *)psCleanup->psHW2DContextMemInfo->pvLinAddrKM;
     pDst += ui32OffsetToPDDevPAddr;
@@ -1346,7 +1683,7 @@ IMG_HANDLE SGXRegisterHW2DContextKM(IMG_HANDLE                            hDeviceNode,
     }
 
 #if defined(PDUMP)
-    
+    /* PDUMP the HW 2D Context */
        PDUMPCOMMENTWITHFLAGS(PDUMP_FLAGS_CONTINUOUS, "HW 2D context struct");
 
        PDUMPMEM(
@@ -1357,7 +1694,7 @@ IMG_HANDLE SGXRegisterHW2DContextKM(IMG_HANDLE                            hDeviceNode,
         PDUMP_FLAGS_CONTINUOUS, 
         MAKEUNIQUETAG(psCleanup->psHW2DContextMemInfo));
 
-    
+    /* PDUMP the PDDevPAddr */
        PDUMPCOMMENT("Page directory address in HW 2D transfer context");
     PDUMPPDDEVPADDR(
             psCleanup->psHW2DContextMemInfo,
@@ -1369,6 +1706,7 @@ IMG_HANDLE SGXRegisterHW2DContextKM(IMG_HANDLE                            hDeviceNode,
 
        psCleanup->hBlockAlloc = hBlockAlloc;
        psCleanup->psDeviceNode = psDeviceNode;
+       psCleanup->bCleanupTimerRunning = IMG_FALSE;
 
        psResItem = ResManRegisterRes(psPerProc->hResManContext,
                                                                  RESMAN_TYPE_HW_2D_CONTEXT,
@@ -1386,6 +1724,7 @@ IMG_HANDLE SGXRegisterHW2DContextKM(IMG_HANDLE                            hDeviceNode,
 
        return (IMG_HANDLE)psCleanup;
 
+/* Error exit paths */
 exit2:
     PVRSRVFreeDeviceMemKM(hDeviceNode,
                          psCleanup->psHW2DContextMemInfo);
@@ -1394,7 +1733,7 @@ exit1:
               sizeof(SGX_HW_2D_CONTEXT_CLEANUP),
               psCleanup,
               psCleanup->hBlockAlloc);
-    
+    /*not nulling pointer, out of scope*/
 exit0:
     return IMG_NULL;
 }
@@ -1418,8 +1757,16 @@ PVRSRV_ERROR SGXUnregisterHW2DContextKM(IMG_HANDLE hHW2DContext, IMG_BOOL bForce
 
        return eError;
 }
-#endif 
+#endif /* #if defined(SGX_FEATURE_2D_HARDWARE)*/
 
+/*!****************************************************************************
+ @Function     SGX2DQuerySyncOpsCompleteKM
+
+ @Input                psSyncInfo : Sync object to be queried
+
+ @Return       IMG_TRUE - ops complete, IMG_FALSE - ops pending
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(SGX2DQuerySyncOpsComplete)
 #endif
@@ -1436,6 +1783,16 @@ IMG_BOOL SGX2DQuerySyncOpsComplete(PVRSRV_KERNEL_SYNC_INFO       *psSyncInfo,
                                         );
 }
 
+/*!****************************************************************************
+ @Function     SGX2DQueryBlitsCompleteKM
+
+ @Input                psDevInfo : SGX device info structure
+
+ @Input                psSyncInfo : Sync object to be queried
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 IMG_EXPORT
 PVRSRV_ERROR SGX2DQueryBlitsCompleteKM(PVRSRV_SGXDEV_INFO      *psDevInfo,
                                                                           PVRSRV_KERNEL_SYNC_INFO *psSyncInfo,
@@ -1452,20 +1809,20 @@ PVRSRV_ERROR SGX2DQueryBlitsCompleteKM(PVRSRV_SGXDEV_INFO       *psDevInfo,
 
        if(SGX2DQuerySyncOpsComplete(psSyncInfo, ui32ReadOpsPending, ui32WriteOpsPending))
        {
-               
+               /* Instant success */
                PVR_DPF((PVR_DBG_CALLTRACE, "SGX2DQueryBlitsCompleteKM: No wait. Blits complete."));
                return PVRSRV_OK;
        }
 
-       
+       /* Not complete yet */
        if (!bWaitForComplete)
        {
-               
+               /* Just report not complete */
                PVR_DPF((PVR_DBG_CALLTRACE, "SGX2DQueryBlitsCompleteKM: No wait. Ops pending."));
                return PVRSRV_ERROR_CMD_NOT_PROCESSED;
        }
 
-       
+       /* Start polling */
        PVR_DPF((PVR_DBG_MESSAGE, "SGX2DQueryBlitsCompleteKM: Ops pending. Start polling."));
 
        LOOP_UNTIL_TIMEOUT(MAX_HW_TIME_US)
@@ -1474,7 +1831,7 @@ PVRSRV_ERROR SGX2DQueryBlitsCompleteKM(PVRSRV_SGXDEV_INFO *psDevInfo,
 
                if(SGX2DQuerySyncOpsComplete(psSyncInfo, ui32ReadOpsPending, ui32WriteOpsPending))
                {
-                       
+                       /* Success */
                        PVR_DPF((PVR_DBG_CALLTRACE, "SGX2DQueryBlitsCompleteKM: Wait over.  Blits complete."));
                        return PVRSRV_OK;
                }
@@ -1482,7 +1839,7 @@ PVRSRV_ERROR SGX2DQueryBlitsCompleteKM(PVRSRV_SGXDEV_INFO *psDevInfo,
                OSSleepms(1);
        } END_LOOP_UNTIL_TIMEOUT();
 
-       
+       /* Timed out */
        PVR_DPF((PVR_DBG_ERROR,"SGX2DQueryBlitsCompleteKM: Timed out. Ops pending."));
 
 #if defined(DEBUG)
@@ -1533,54 +1890,21 @@ IMG_UINT32 SGXConvertTimeStamp(PVRSRV_SGXDEV_INFO       *psDevInfo,
        ui32Clocksx16 = (IMG_UINT32)(ui64Clocks / 16);
 
        return ui32Clocksx16;
-#endif 
+#endif /* EUR_CR_TIMER */
 }
 
 
 IMG_VOID SGXWaitClocks(PVRSRV_SGXDEV_INFO      *psDevInfo,
                                           IMG_UINT32                   ui32SGXClocks)
 {
-       
-
+       /*
+               Round up to the next microsecond.
+       */
        OSWaitus(1 + (ui32SGXClocks * 1000000 / psDevInfo->ui32CoreClockSpeed));
 }
 
 
 
-IMG_EXPORT
-PVRSRV_ERROR PVRSRVGetSGXRevDataKM(PVRSRV_DEVICE_NODE* psDeviceNode, IMG_UINT32 *pui32SGXCoreRev,
-                               IMG_UINT32 *pui32SGXCoreID)
-{
-       PVRSRV_SGXDEV_INFO *psDevInfo = (PVRSRV_SGXDEV_INFO *)psDeviceNode->pvDevice;
-       SGX_MISC_INFO sMiscInfo;
-       PVRSRV_ERROR eError;
-
-       sMiscInfo.eRequest = SGX_MISC_INFO_REQUEST_SGXREV;
-       eError = SGXGetMiscInfoKM(psDevInfo, &sMiscInfo, psDeviceNode, NULL);
-
-       *pui32SGXCoreRev = sMiscInfo.uData.sSGXFeatures.ui32CoreRev;
-       *pui32SGXCoreID = sMiscInfo.uData.sSGXFeatures.ui32CoreID;
-       return eError;
-}
-
-
-PVRSRV_ERROR SGXContextSuspend(PVRSRV_DEVICE_NODE      *psDeviceNode,
-                                                          IMG_DEV_VIRTADDR             *psHWContextDevVAddr,
-                                                          IMG_BOOL                             bResume)
-{
-       PVRSRV_ERROR            eError;
-       SGXMKIF_COMMAND         sCommand = {0};
-
-       sCommand.ui32Data[0] = psHWContextDevVAddr->uiAddr;
-       sCommand.ui32Data[1] = bResume ? PVRSRV_CTXSUSPCMD_RESUME : PVRSRV_CTXSUSPCMD_SUSPEND;
-
-       eError = SGXScheduleCCBCommandKM(psDeviceNode, SGXMKIF_CMD_CONTEXTSUSPEND, &sCommand, KERNEL_ID, 0, IMG_NULL, IMG_FALSE);
-       if (eError != PVRSRV_OK)
-       {
-               PVR_DPF((PVR_DBG_ERROR,"SGXContextSuspend: Failed to submit context suspend command"));
-               return eError;
-       }
-
-       return eError;
-}
-
+/******************************************************************************
+ End of file (sgxutils.c)
+******************************************************************************/
index ae6dbc7..fc2ef6f 100644 (file)
@@ -1,33 +1,49 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Device specific utility routines declarations
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Inline functions/structures specific to SGX
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "perproc.h"
 #include "sgxinfokm.h"
 
+/* PRQA S 3410 7 */ /* macros require the absence of some brackets */
 #define CCB_OFFSET_IS_VALID(type, psCCBMemInfo, psCCBKick, offset) \
        ((sizeof(type) <= (psCCBMemInfo)->uAllocSize) && \
        ((psCCBKick)->offset <= (psCCBMemInfo)->uAllocSize - sizeof(type)))
@@ -36,6 +52,8 @@
        ((type *)(((IMG_CHAR *)(psCCBMemInfo)->pvLinAddrKM) + \
                (psCCBKick)->offset))
 
+extern IMG_UINT64 ui64KickCount;
+
 
 IMG_IMPORT
 IMG_VOID SGXTestActivePowerEvent(PVRSRV_DEVICE_NODE    *psDeviceNode,
@@ -123,6 +141,21 @@ IMG_UINT32 SGXConvertTimeStamp(PVRSRV_SGXDEV_INFO  *psDevInfo,
                                                           IMG_UINT32                   ui32TimeWraps,
                                                           IMG_UINT32                   ui32Time);
 
+/*!
+*******************************************************************************
+
+ @Function     SGXWaitClocks
+
+ @Description
+
+ Wait for a specified number of SGX clock cycles to elapse.
+
+ @Input psDevInfo - SGX Device Info
+ @Input ui32SGXClocks - number of clock cycles to wait
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 IMG_VOID SGXWaitClocks(PVRSRV_SGXDEV_INFO      *psDevInfo,
                                           IMG_UINT32                   ui32SGXClocks);
 
@@ -135,7 +168,28 @@ IMG_IMPORT
 PVRSRV_ERROR PVRSRVGetSGXRevDataKM(PVRSRV_DEVICE_NODE* psDeviceNode, IMG_UINT32 *pui32SGXCoreRev,
                                IMG_UINT32 *pui32SGXCoreID);
 
+/*!
+******************************************************************************
+
+ @Function     SGXContextSuspend
+
+ @Description - Interface to the SGX microkernel to instruct it to suspend or
+                               resume processing on a given context. This will interrupt current
+                               processing of this context if a task is already running and is
+                               interruptable.
+
+ @Input psDeviceNode                   SGX device node
+ @Input psHWContextDevVAddr            SGX virtual address of the context to be suspended
+                                                               or resumed. Can be of type SGXMKIF_HWRENDERCONTEXT,
+                                                               SGXMKIF_HWTRANSFERCONTEXT or SGXMKIF_HW2DCONTEXT
+ @Input bResume                                        IMG_TRUE to put a context into suspend state,
+                                                               IMG_FALSE to resume a previously suspended context
+
+******************************************************************************/
 PVRSRV_ERROR SGXContextSuspend(PVRSRV_DEVICE_NODE      *psDeviceNode,
                                                           IMG_DEV_VIRTADDR             *psHWContextDevVAddr,
                                                           IMG_BOOL                             bResume);
 
+/******************************************************************************
+ End of file (sgxutils.h)
+******************************************************************************/
index 65e71d1..a2a47a8 100644 (file)
@@ -1,26 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 pvrsrvkm-y += \
        services4/srvkm/env/linux/osfunc.o \
@@ -40,22 +56,36 @@ pvrsrvkm-y += \
        services4/srvkm/common/deviceclass.o \
        services4/srvkm/common/handle.o \
        services4/srvkm/common/hash.o \
+       services4/srvkm/common/lists.o \
+       services4/srvkm/common/mem.o \
+       services4/srvkm/common/mem_debug.o \
        services4/srvkm/common/metrics.o \
+       services4/srvkm/common/osfunc_common.o \
+       services4/srvkm/common/pdump_common.o \
+       services4/srvkm/common/perproc.o \
+       services4/srvkm/common/power.o \
        services4/srvkm/common/pvrsrv.o \
        services4/srvkm/common/queue.o \
        services4/srvkm/common/ra.o \
+       services4/srvkm/common/refcount.o \
        services4/srvkm/common/resman.o \
-       services4/srvkm/common/power.o \
-       services4/srvkm/common/mem.o \
-       services4/srvkm/common/pdump_common.o \
        services4/srvkm/bridged/bridged_support.o \
        services4/srvkm/bridged/bridged_pvr_bridge.o \
-       services4/srvkm/common/perproc.o \
        services4/system/$(PVR_SYSTEM)/sysconfig.o \
-       services4/system/$(PVR_SYSTEM)/sysutils.o \
-       services4/srvkm/common/lists.o \
-       services4/srvkm/common/mem_debug.o \
-       services4/srvkm/common/osfunc_common.o
+       services4/system/$(PVR_SYSTEM)/sysutils.o
+
+pvrsrvkm-$(CONFIG_ION_OMAP) += \
+       services4/srvkm/env/linux/ion.o
+
+ifeq ($(SUPPORT_ION),1)
+pvrsrvkm-y += \
+       services4/srvkm/env/linux/ion.o
+endif
+
+ifeq ($(TTRACE),1)
+pvrsrvkm-y += \
+       services4/srvkm/common/ttrace.o
+endif
 
 ifneq ($(W),1)
 CFLAGS_osfunc.o := -Werror
@@ -89,6 +119,7 @@ CFLAGS_perproc.o := -Werror
 CFLAGS_lists.o := -Werror
 CFLAGS_mem_debug.o := -Werror
 CFLAGS_osfunc_common.o := -Werror
+CFLAGS_refcount.o := -Werror
 endif
 
 # SUPPORT_SGX==1 only
index 7eee6bc..535a1f9 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 modules := srvkm
 
index 7716529..b838809 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Environmental Data header file
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Linux-specific part of system data.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef _ENV_DATA_
 #define _ENV_DATA_
 
 #include <linux/workqueue.h>
 #endif
 
+/* 
+ *     Env data specific to linux - convenient place to put this
+ */
+
+/* Fairly arbitrary sizes - hopefully enough for all bridge calls */
 #define PVRSRV_MAX_BRIDGE_IN_SIZE      0x1000
 #define PVRSRV_MAX_BRIDGE_OUT_SIZE     0x1000
 
@@ -61,6 +81,13 @@ typedef struct _ENV_DATA_TAG
 #else
        struct tasklet_struct   sMISRTasklet;
 #endif
+#if defined (SUPPORT_ION)
+       IMG_HANDLE              hIonHeaps;
+       IMG_HANDLE              hIonDev;
+#endif
 } ENV_DATA;
 
-#endif 
+#endif /* _ENV_DATA_ */
+/*****************************************************************************
+ End of file (env_data.h)
+*****************************************************************************/
index dabf1e3..8a37a7f 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OS specific per process data interface
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Linux per process data
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __ENV_PERPROC_H__
 #define __ENV_PERPROC_H__
 
@@ -33,6 +48,7 @@
 #include "services.h"
 #include "handle.h"
 
+#define ION_CLIENT_NAME_SIZE   50
 typedef struct _PVRSRV_ENV_PER_PROCESS_DATA_
 {
        IMG_HANDLE hBlockAlloc;
@@ -40,6 +56,10 @@ typedef struct _PVRSRV_ENV_PER_PROCESS_DATA_
 #if defined(SUPPORT_DRI_DRM) && defined(PVR_SECURE_DRM_AUTH_EXPORT)
        struct list_head sDRMAuthListHead;
 #endif
+#if defined (SUPPORT_ION)
+       struct ion_client *psIONClient;
+       IMG_CHAR azIonClientName[ION_CLIENT_NAME_SIZE];
+#endif
 } PVRSRV_ENV_PER_PROCESS_DATA;
 
 IMG_VOID RemovePerProcessProcDir(PVRSRV_ENV_PER_PROCESS_DATA *psEnvPerProc);
@@ -52,5 +72,8 @@ PVRSRV_ERROR LinuxMMapPerProcessHandleOptions(PVRSRV_HANDLE_BASE *psHandleBase);
 
 IMG_HANDLE LinuxTerminatingProcessPrivateData(IMG_VOID);
 
-#endif 
+#endif /* __ENV_PERPROC_H__ */
 
+/******************************************************************************
+ End of file (env_perproc.h)
+******************************************************************************/
index 7e160c3..b70a79d 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Event Object 
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 
@@ -85,6 +100,20 @@ typedef struct PVRSRV_LINUX_EVENT_OBJECT_TAG
        PVRSRV_LINUX_EVENT_OBJECT_LIST *psLinuxEventObjectList;
 } PVRSRV_LINUX_EVENT_OBJECT;
 
+/*!
+******************************************************************************
+
+ @Function     LinuxEventObjectListCreate
+ @Description 
+ Linux wait object list creation
+
+ @Output    hOSEventKM : Pointer to the event object list handle 
+ @Return   PVRSRV_ERROR  :  Error code
+
+******************************************************************************/
 PVRSRV_ERROR LinuxEventObjectListCreate(IMG_HANDLE *phEventObjectList)
 {
        PVRSRV_LINUX_EVENT_OBJECT_LIST *psEventObjectList;
@@ -106,6 +135,20 @@ PVRSRV_ERROR LinuxEventObjectListCreate(IMG_HANDLE *phEventObjectList)
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     LinuxEventObjectListDestroy
+ @Description 
+ Linux wait object list destruction
+
+ @Input    hOSEventKM : Event object list handle 
+ @Return   PVRSRV_ERROR  :  Error code
+
+******************************************************************************/
 PVRSRV_ERROR LinuxEventObjectListDestroy(IMG_HANDLE hEventObjectList)
 {
 
@@ -126,13 +169,29 @@ PVRSRV_ERROR LinuxEventObjectListDestroy(IMG_HANDLE hEventObjectList)
                }
 
                OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP, sizeof(PVRSRV_LINUX_EVENT_OBJECT_LIST), psEventObjectList, IMG_NULL);
-               
+               /*not nulling pointer, copy on stack*/
        }
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     LinuxEventObjectDelete
+ @Description 
+ Linux wait object removal
+ @Input    hOSEventObjectList : Event object list handle 
+ @Input    hOSEventObject : Event object handle 
+ @Input    bResManCallback : Called from the resman
+ @Return   PVRSRV_ERROR  :  Error code
+
+******************************************************************************/
 PVRSRV_ERROR LinuxEventObjectDelete(IMG_HANDLE hOSEventObjectList, IMG_HANDLE hOSEventObject)
 {
        if(hOSEventObjectList)
@@ -155,6 +214,20 @@ PVRSRV_ERROR LinuxEventObjectDelete(IMG_HANDLE hOSEventObjectList, IMG_HANDLE hO
 
 }
 
+/*!
+******************************************************************************
+
+ @Function     LinuxEventObjectDeleteCallback
+ @Description 
+ Linux wait object removal
+ @Input    hOSEventObject : Event object handle 
+ @Return   PVRSRV_ERROR  :  Error code
+
+******************************************************************************/
 static PVRSRV_ERROR LinuxEventObjectDeleteCallback(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bForceCleanup)
 {
        PVRSRV_LINUX_EVENT_OBJECT *psLinuxEventObject = pvParam;
@@ -173,10 +246,25 @@ static PVRSRV_ERROR LinuxEventObjectDeleteCallback(IMG_PVOID pvParam, IMG_UINT32
 #endif 
 
        OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP, sizeof(PVRSRV_LINUX_EVENT_OBJECT), psLinuxEventObject, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
        return PVRSRV_OK;
 }
+/*!
+******************************************************************************
+
+ @Function     LinuxEventObjectAdd
+ @Description 
+ Linux wait object addition
+
+ @Input    hOSEventObjectList : Event object list handle 
+ @Output   phOSEventObject : Pointer to the event object handle 
+ @Return   PVRSRV_ERROR  :  Error code
+
+******************************************************************************/
 PVRSRV_ERROR LinuxEventObjectAdd(IMG_HANDLE hOSEventObjectList, IMG_HANDLE *phOSEventObject)
  {
        PVRSRV_LINUX_EVENT_OBJECT *psLinuxEventObject; 
@@ -192,7 +280,7 @@ PVRSRV_ERROR LinuxEventObjectAdd(IMG_HANDLE hOSEventObjectList, IMG_HANDLE *phOS
                return PVRSRV_ERROR_OUT_OF_MEMORY;
        }
 
-       
+       /* allocate completion variable */
        if(OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP, sizeof(PVRSRV_LINUX_EVENT_OBJECT), 
                (IMG_VOID **)&psLinuxEventObject, IMG_NULL,
                "Linux Event Object") != PVRSRV_OK)
@@ -228,6 +316,20 @@ PVRSRV_ERROR LinuxEventObjectAdd(IMG_HANDLE hOSEventObjectList, IMG_HANDLE *phOS
        return PVRSRV_OK;        
 }
 
+/*!
+******************************************************************************
+
+ @Function     LinuxEventObjectSignal
+ @Description 
+ Linux wait object signaling function
+ @Input    hOSEventObjectList : Event object list handle 
+ @Return   PVRSRV_ERROR  :  Error code
+
+******************************************************************************/
 PVRSRV_ERROR LinuxEventObjectSignal(IMG_HANDLE hOSEventObjectList)
 {
        PVRSRV_LINUX_EVENT_OBJECT *psLinuxEventObject;
@@ -236,7 +338,10 @@ PVRSRV_ERROR LinuxEventObjectSignal(IMG_HANDLE hOSEventObjectList)
 
        psList = &psLinuxEventObjectList->sList;
 
-       
+       /*
+        * We don't take the write lock in interrupt context, so we don't
+        * need to use read_lock_irqsave.
+        */
        read_lock(&psLinuxEventObjectList->sLock);
        list_for_each(psListEntry, psList) 
        {               
@@ -252,6 +357,22 @@ PVRSRV_ERROR LinuxEventObjectSignal(IMG_HANDLE hOSEventObjectList)
        
 }
 
+/*!
+******************************************************************************
+
+ @Function     LinuxEventObjectWait
+ @Description 
+ Linux wait object routine
+ @Input    hOSEventObject : Event object handle 
+ @Input   ui32MSTimeout : Time out value in msec
+
+ @Return   PVRSRV_ERROR  :  Error code
+
+******************************************************************************/
 PVRSRV_ERROR LinuxEventObjectWait(IMG_HANDLE hOSEventObject, IMG_UINT32 ui32MSTimeout)
 {
        IMG_UINT32 ui32TimeStamp;
index 3035283..5c1451c 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Event Object 
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
 
 PVRSRV_ERROR LinuxEventObjectListCreate(IMG_HANDLE *phEventObjectList);
 PVRSRV_ERROR LinuxEventObjectListDestroy(IMG_HANDLE hEventObjectList);
index e64012c..55cd4f0 100644 (file)
@@ -1,29 +1,46 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux specific Services code internal interfaces
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Interfaces between various parts of the Linux specific
+                Services code, that don't have any other obvious
+                header file to go into.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __LINKAGE_H__
 #define __LINKAGE_H__
 
@@ -45,8 +62,11 @@ IMG_INT PVRProcSetPowerLevel(struct file *file, const IMG_CHAR *buffer, IMG_UINT
 
 void ProcSeqShowPowerLevel(struct seq_file *sfile,void* el);
 
-#endif 
+#endif /* PVR_MANUAL_POWER_CONTROL */
 
-#endif 
+#endif /* DEBUG */
 
-#endif 
+#endif /* __LINKAGE_H__ */
+/*****************************************************************************
+ End of file (linkage.h)
+*****************************************************************************/
index a0854c3..11adcaa 100644 (file)
@@ -1,32 +1,56 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Main driver lock
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    The main driver lock, held in most places in
+                the driver.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __LOCK_H__
 #define __LOCK_H__
 
+/*
+ * Main driver lock, used to ensure driver code is single threaded.
+ * There are some places where this lock must not be taken, such as
+ * in the mmap related deriver entry points.
+ */
 extern PVRSRV_LINUX_MUTEX gPVRSRVLock;
 
-#endif 
+#endif /* __LOCK_H__ */
+/*****************************************************************************
+ End of file (lock.h)
+*****************************************************************************/
index 3b59aec..23ae762 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Misc memory management utility functions for Linux
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 
 #endif
 #endif
 
+#if !defined(PVR_LINUX_MEM_AREA_POOL_MAX_PAGES)
+#define PVR_LINUX_MEM_AREA_POOL_MAX_PAGES 0
+#endif
+
+#include <linux/kernel.h>
+#include <asm/atomic.h>
+#include <linux/list.h>
+#include <linux/mutex.h>
 #include <linux/mm.h>
 #include <linux/vmalloc.h>
 #include <asm/io.h>
 #include <linux/highmem.h>
 #include <linux/sched.h>
 
+#if defined(PVR_LINUX_MEM_AREA_POOL_ALLOW_SHRINK)
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,1,0))
+#include <linux/shrinker.h>
+#endif
+#endif
+
 #include "img_defs.h"
 #include "services.h"
 #include "servicesint.h"
        #include "lists.h"
 #endif
 
+/*
+ * The page pool entry count is an atomic int so that the shrinker function
+ * can return it even when we can't take the lock that protects the page pool
+ * list.
+ */
+static atomic_t g_sPagePoolEntryCount = ATOMIC_INIT(0);
+
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 typedef enum {
     DEBUG_MEM_ALLOC_TYPE_KMALLOC,
@@ -68,13 +104,17 @@ typedef enum {
     DEBUG_MEM_ALLOC_TYPE_IOREMAP,
     DEBUG_MEM_ALLOC_TYPE_IO,
     DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE,
+    DEBUG_MEM_ALLOC_TYPE_ION,
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+    DEBUG_MEM_ALLOC_TYPE_VMAP,
+#endif
     DEBUG_MEM_ALLOC_TYPE_COUNT
-}DEBUG_MEM_ALLOC_TYPE;
+} DEBUG_MEM_ALLOC_TYPE;
 
 typedef struct _DEBUG_MEM_ALLOC_REC
 {
     DEBUG_MEM_ALLOC_TYPE    eAllocType;
-       IMG_VOID                                *pvKey; 
+       IMG_VOID                                *pvKey; /* Some unique value (private to the eAllocType) */
     IMG_VOID                *pvCpuVAddr;
     IMG_UINT32              ulCpuPAddr;
     IMG_VOID                *pvPrivateData;
@@ -85,7 +125,7 @@ typedef struct _DEBUG_MEM_ALLOC_REC
     
     struct _DEBUG_MEM_ALLOC_REC   *psNext;
        struct _DEBUG_MEM_ALLOC_REC   **ppsThis;
-}DEBUG_MEM_ALLOC_REC;
+} DEBUG_MEM_ALLOC_REC;
 
 static IMPLEMENT_LIST_ANY_VA_2(DEBUG_MEM_ALLOC_REC, IMG_BOOL, IMG_FALSE)
 static IMPLEMENT_LIST_ANY_VA(DEBUG_MEM_ALLOC_REC)
@@ -99,9 +139,17 @@ static DEBUG_MEM_ALLOC_REC *g_MemoryRecords;
 static IMG_UINT32 g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_COUNT];
 static IMG_UINT32 g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_COUNT];
 
-static IMG_UINT32 g_SysRAMWaterMark;
-static IMG_UINT32 g_SysRAMHighWaterMark;
+/* vmalloc + kmalloc + alloc_pages + kmem_cache */
+static IMG_UINT32 g_SysRAMWaterMark;           /* Doesn't include page pool */
+static IMG_UINT32 g_SysRAMHighWaterMark;       /* *DOES* include page pool */
 
+static inline IMG_UINT32
+SysRAMTrueWaterMark(void)
+{
+       return g_SysRAMWaterMark + PAGES_TO_BYTES(atomic_read(&g_sPagePoolEntryCount));
+}
+
+/* ioremap + io */
 static IMG_UINT32 g_IOMemWaterMark;
 static IMG_UINT32 g_IOMemHighWaterMark;
 
@@ -119,7 +167,7 @@ static IMG_VOID DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE eAllocType, IMG_V
 static IMG_CHAR *DebugMemAllocRecordTypeToString(DEBUG_MEM_ALLOC_TYPE eAllocType);
 
 
-static struct proc_dir_entry *g_SeqFileMemoryRecords =0;
+static struct proc_dir_entry *g_SeqFileMemoryRecords;
 static void* ProcSeqNextMemoryRecords(struct seq_file *sfile,void* el,loff_t off);
 static void ProcSeqShowMemoryRecords(struct seq_file *sfile,void* el);
 static void* ProcSeqOff2ElementMemoryRecords(struct seq_file * sfile, loff_t off);
@@ -153,7 +201,7 @@ static IMG_UINT32 g_LinuxMemAreaWaterMark;
 static IMG_UINT32 g_LinuxMemAreaHighWaterMark;
 
 
-static struct proc_dir_entry *g_SeqFileMemArea=0;
+static struct proc_dir_entry *g_SeqFileMemArea;
 
 static void* ProcSeqNextMemArea(struct seq_file *sfile,void* el,loff_t off);
 static void ProcSeqShowMemArea(struct seq_file *sfile,void* el);
@@ -169,8 +217,19 @@ static PVRSRV_LINUX_MUTEX g_sDebugMutex;
 static void ProcSeqStartstopDebugMutex(struct seq_file *sfile,IMG_BOOL start);
 #endif
 
-static LinuxKMemCache *psLinuxMemAreaCache;
+typedef        struct
+{
+       /* Linkage for page pool LRU list */
+       struct list_head sPagePoolItem;
+
+       struct page *psPage;
+} LinuxPagePoolEntry;
+
+static LinuxKMemCache *g_PsLinuxMemAreaCache;
+static LinuxKMemCache *g_PsLinuxPagePoolCache;
 
+static LIST_HEAD(g_sPagePoolList);
+static int g_iPagePoolMaxEntries;
 
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15))
 static IMG_VOID ReservePages(IMG_VOID *pvAddress, IMG_UINT32 ui32Length);
@@ -185,165 +244,26 @@ static DEBUG_LINUX_MEM_AREA_REC *DebugLinuxMemAreaRecordFind(LinuxMemArea *psLin
 static IMG_VOID DebugLinuxMemAreaRecordRemove(LinuxMemArea *psLinuxMemArea);
 #endif
 
-PVRSRV_ERROR
-LinuxMMInit(IMG_VOID)
-{
-#if defined(DEBUG_LINUX_MEM_AREAS) || defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-       LinuxInitMutex(&g_sDebugMutex);
-#endif
-
-#if defined(DEBUG_LINUX_MEM_AREAS)
-    {
-               g_SeqFileMemArea = CreateProcReadEntrySeq(
-                                                                       "mem_areas", 
-                                                                       NULL, 
-                                                                       ProcSeqNextMemArea,
-                                                                       ProcSeqShowMemArea,
-                                                                       ProcSeqOff2ElementMemArea,
-                                                                       ProcSeqStartstopDebugMutex
-                                                                  );
-               if(!g_SeqFileMemArea)
-        {
-            return PVRSRV_ERROR_OUT_OF_MEMORY;
-        }
-    }
-#endif
-
-
-#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    {
-               g_SeqFileMemoryRecords =CreateProcReadEntrySeq(
-                                                                       "meminfo", 
-                                                                       NULL, 
-                                                                       ProcSeqNextMemoryRecords,
-                                                                       ProcSeqShowMemoryRecords, 
-                                                                       ProcSeqOff2ElementMemoryRecords,
-                                                                       ProcSeqStartstopDebugMutex
-                                                                  );
-        if(!g_SeqFileMemoryRecords)
-        {
-            return PVRSRV_ERROR_OUT_OF_MEMORY;
-        }
-    }
-#endif
-
-    psLinuxMemAreaCache = KMemCacheCreateWrapper("img-mm", sizeof(LinuxMemArea), 0, 0);
-    if(!psLinuxMemAreaCache)
-    {
-        PVR_DPF((PVR_DBG_ERROR,"%s: failed to allocate kmem_cache", __FUNCTION__));
-        return PVRSRV_ERROR_OUT_OF_MEMORY;
-    }
-
-    return PVRSRV_OK;
-}
-
-#if defined(DEBUG_LINUX_MEM_AREAS)
-static IMG_VOID LinuxMMCleanup_MemAreas_ForEachCb(DEBUG_LINUX_MEM_AREA_REC *psCurrentRecord)
-{
-       LinuxMemArea *psLinuxMemArea;
-
-       psLinuxMemArea = psCurrentRecord->psLinuxMemArea;
-       PVR_DPF((PVR_DBG_ERROR, "%s: BUG!: Cleaning up Linux memory area (%p), type=%s, size=%d bytes",
-                               __FUNCTION__,
-                               psCurrentRecord->psLinuxMemArea,
-                               LinuxMemAreaTypeToString(psCurrentRecord->psLinuxMemArea->eAreaType),
-                               psCurrentRecord->psLinuxMemArea->ui32ByteSize));
-       
-       LinuxMemAreaDeepFree(psLinuxMemArea);
-}
-#endif
-
-#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-static IMG_VOID LinuxMMCleanup_MemRecords_ForEachVa(DEBUG_MEM_ALLOC_REC *psCurrentRecord)
 
+static inline IMG_BOOL
+AreaIsUncached(IMG_UINT32 ui32AreaFlags)
 {
-       
-       PVR_DPF((PVR_DBG_ERROR, "%s: BUG!: Cleaning up memory: "
-                                                       "type=%s "
-                                                       "CpuVAddr=%p "
-                                                       "CpuPAddr=0x%08x, "
-                                                       "allocated @ file=%s,line=%d",
-                       __FUNCTION__,
-                       DebugMemAllocRecordTypeToString(psCurrentRecord->eAllocType),
-                       psCurrentRecord->pvCpuVAddr,
-                       psCurrentRecord->ulCpuPAddr,
-                       psCurrentRecord->pszFileName,
-                       psCurrentRecord->ui32Line));
-       switch(psCurrentRecord->eAllocType)
-       {
-               case DEBUG_MEM_ALLOC_TYPE_KMALLOC:
-                       KFreeWrapper(psCurrentRecord->pvCpuVAddr);
-                       break;
-               case DEBUG_MEM_ALLOC_TYPE_IOREMAP:
-                       IOUnmapWrapper(psCurrentRecord->pvCpuVAddr);
-                       break;
-               case DEBUG_MEM_ALLOC_TYPE_IO:
-                       
-                       DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_IO, psCurrentRecord->pvKey, __FILE__, __LINE__);
-                       break;
-               case DEBUG_MEM_ALLOC_TYPE_VMALLOC:
-                       VFreeWrapper(psCurrentRecord->pvCpuVAddr);
-                       break;
-               case DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES:
-                       
-                       DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES, psCurrentRecord->pvKey, __FILE__, __LINE__);
-                       break;
-               case DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE:
-                       KMemCacheFreeWrapper(psCurrentRecord->pvPrivateData, psCurrentRecord->pvCpuVAddr);
-                       break;
-               default:
-                       PVR_ASSERT(0);
-       }
+       return (ui32AreaFlags & (PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_UNCACHED)) != 0;
 }
-#endif
-
 
-IMG_VOID
-LinuxMMCleanup(IMG_VOID)
+static inline IMG_BOOL
+CanFreeToPool(LinuxMemArea *psLinuxMemArea)
 {
-
-#if defined(DEBUG_LINUX_MEM_AREAS)
-    {
-        if(g_LinuxMemAreaCount)
-        {
-            PVR_DPF((PVR_DBG_ERROR, "%s: BUG!: There are %d LinuxMemArea allocation unfreed (%d bytes)",
-                    __FUNCTION__, g_LinuxMemAreaCount, g_LinuxMemAreaWaterMark));
-        }
-               
-               List_DEBUG_LINUX_MEM_AREA_REC_ForEach(g_LinuxMemAreaRecords,
-                                                                                       LinuxMMCleanup_MemAreas_ForEachCb);
-
-               RemoveProcEntrySeq( g_SeqFileMemArea );
-    }
-#endif
-
-
-#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    {
-        
-        
-               List_DEBUG_MEM_ALLOC_REC_ForEach(g_MemoryRecords,
-                                                                               LinuxMMCleanup_MemRecords_ForEachVa);
-
-               RemoveProcEntrySeq( g_SeqFileMemoryRecords );
-    }
-#endif
-
-    if(psLinuxMemAreaCache)
-    {
-        KMemCacheDestroyWrapper(psLinuxMemAreaCache); 
-        psLinuxMemAreaCache=NULL;
-    }
+       return AreaIsUncached(psLinuxMemArea->ui32AreaFlags) && !psLinuxMemArea->bNeedsCacheInvalidate;
 }
 
-
 IMG_VOID *
 _KMallocWrapper(IMG_UINT32 ui32ByteSize, gfp_t uFlags, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
 {
     IMG_VOID *pvRet;
     pvRet = kmalloc(ui32ByteSize, uFlags);
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    if(pvRet)
+    if (pvRet)
     {
         DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE_KMALLOC,
                                pvRet,
@@ -353,7 +273,7 @@ _KMallocWrapper(IMG_UINT32 ui32ByteSize, gfp_t uFlags, IMG_CHAR *pszFileName, IM
                                ui32ByteSize,
                                pszFileName,
                                ui32Line
-                               );
+                              );
     }
 #else
     PVR_UNREFERENCED_PARAMETER(pszFileName);
@@ -406,27 +326,31 @@ DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE eAllocType,
        List_DEBUG_MEM_ALLOC_REC_Insert(&g_MemoryRecords, psRecord);
     
     g_WaterMarkData[eAllocType] += ui32Bytes;
-    if(g_WaterMarkData[eAllocType] > g_HighWaterMarkData[eAllocType])
+    if (g_WaterMarkData[eAllocType] > g_HighWaterMarkData[eAllocType])
     {
         g_HighWaterMarkData[eAllocType] = g_WaterMarkData[eAllocType];
     }
 
-    if(eAllocType == DEBUG_MEM_ALLOC_TYPE_KMALLOC
+    if (eAllocType == DEBUG_MEM_ALLOC_TYPE_KMALLOC
        || eAllocType == DEBUG_MEM_ALLOC_TYPE_VMALLOC
        || eAllocType == DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES
        || eAllocType == DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE)
     {
+       IMG_UINT32 ui32SysRAMTrueWaterMark;
+
         g_SysRAMWaterMark += ui32Bytes;
-        if(g_SysRAMWaterMark > g_SysRAMHighWaterMark)
+       ui32SysRAMTrueWaterMark = SysRAMTrueWaterMark();
+
+        if (ui32SysRAMTrueWaterMark > g_SysRAMHighWaterMark)
         {
-            g_SysRAMHighWaterMark = g_SysRAMWaterMark;
+            g_SysRAMHighWaterMark = ui32SysRAMTrueWaterMark;
         }
     }
-    else if(eAllocType == DEBUG_MEM_ALLOC_TYPE_IOREMAP
+    else if (eAllocType == DEBUG_MEM_ALLOC_TYPE_IOREMAP
             || eAllocType == DEBUG_MEM_ALLOC_TYPE_IO)
     {
         g_IOMemWaterMark += ui32Bytes;
-        if(g_IOMemWaterMark > g_IOMemHighWaterMark)
+        if (g_IOMemWaterMark > g_IOMemHighWaterMark)
         {
             g_IOMemHighWaterMark = g_IOMemWaterMark;
         }
@@ -444,165 +368,634 @@ static IMG_BOOL DebugMemAllocRecordRemove_AnyVaCb(DEBUG_MEM_ALLOC_REC *psCurrent
        eAllocType = va_arg(va, DEBUG_MEM_ALLOC_TYPE);
        pvKey = va_arg(va, IMG_VOID*);
 
-       if(psCurrentRecord->eAllocType == eAllocType
+       if (psCurrentRecord->eAllocType == eAllocType
                && psCurrentRecord->pvKey == pvKey)
        {
-               eAllocType = psCurrentRecord->eAllocType;
-               g_WaterMarkData[eAllocType] -= psCurrentRecord->ui32Bytes;
-               
-               if(eAllocType == DEBUG_MEM_ALLOC_TYPE_KMALLOC
-                  || eAllocType == DEBUG_MEM_ALLOC_TYPE_VMALLOC
-                  || eAllocType == DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES
-                  || eAllocType == DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE)
+               eAllocType = psCurrentRecord->eAllocType;
+               g_WaterMarkData[eAllocType] -= psCurrentRecord->ui32Bytes;
+               
+               if (eAllocType == DEBUG_MEM_ALLOC_TYPE_KMALLOC
+                  || eAllocType == DEBUG_MEM_ALLOC_TYPE_VMALLOC
+                  || eAllocType == DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES
+                  || eAllocType == DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE)
+               {
+                       g_SysRAMWaterMark -= psCurrentRecord->ui32Bytes;
+               }
+               else if (eAllocType == DEBUG_MEM_ALLOC_TYPE_IOREMAP
+                               || eAllocType == DEBUG_MEM_ALLOC_TYPE_IO)
+               {
+                       g_IOMemWaterMark -= psCurrentRecord->ui32Bytes;
+               }
+               
+               List_DEBUG_MEM_ALLOC_REC_Remove(psCurrentRecord);
+               kfree(psCurrentRecord);
+
+               return IMG_TRUE;
+       }
+       else
+       {
+               return IMG_FALSE;
+       }
+}
+
+
+static IMG_VOID
+DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE eAllocType, IMG_VOID *pvKey, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
+{
+/*    DEBUG_MEM_ALLOC_REC **ppsCurrentRecord;*/
+
+    LinuxLockMutex(&g_sDebugMutex);
+
+    /* Locate the corresponding allocation entry */
+       if (!List_DEBUG_MEM_ALLOC_REC_IMG_BOOL_Any_va(g_MemoryRecords,
+                                                                                               DebugMemAllocRecordRemove_AnyVaCb,
+                                                                                               eAllocType,
+                                                                                               pvKey))
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: couldn't find an entry for type=%s with pvKey=%p (called from %s, line %d\n",
+               __FUNCTION__, DebugMemAllocRecordTypeToString(eAllocType), pvKey,
+               pszFileName, ui32Line));
+       }
+
+    LinuxUnLockMutex(&g_sDebugMutex);
+}
+
+
+static IMG_CHAR *
+DebugMemAllocRecordTypeToString(DEBUG_MEM_ALLOC_TYPE eAllocType)
+{
+    IMG_CHAR *apszDebugMemoryRecordTypes[] = {
+        "KMALLOC",
+        "VMALLOC",
+        "ALLOC_PAGES",
+        "IOREMAP",
+        "IO",
+        "KMEM_CACHE_ALLOC",
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+       "VMAP"
+#endif
+    };
+    return apszDebugMemoryRecordTypes[eAllocType];
+}
+#endif
+
+
+static IMG_BOOL
+AllocFlagsToPGProt(pgprot_t *pPGProtFlags, IMG_UINT32 ui32AllocFlags)
+{
+    pgprot_t PGProtFlags;
+
+    switch (ui32AllocFlags & PVRSRV_HAP_CACHETYPE_MASK)
+    {
+        case PVRSRV_HAP_CACHED:
+            PGProtFlags = PAGE_KERNEL;
+            break;
+        case PVRSRV_HAP_WRITECOMBINE:
+            PGProtFlags = PGPROT_WC(PAGE_KERNEL);
+            break;
+        case PVRSRV_HAP_UNCACHED:
+            PGProtFlags = PGPROT_UC(PAGE_KERNEL);
+            break;
+        default:
+            PVR_DPF((PVR_DBG_ERROR,
+                     "%s: Unknown mapping flags=0x%08x",
+                     __FUNCTION__, ui32AllocFlags));
+            dump_stack();
+            return IMG_FALSE;
+    }
+
+    *pPGProtFlags = PGProtFlags;
+
+    return IMG_TRUE;
+}
+
+IMG_VOID *
+_VMallocWrapper(IMG_UINT32 ui32Bytes,
+                IMG_UINT32 ui32AllocFlags,
+                IMG_CHAR *pszFileName,
+                IMG_UINT32 ui32Line)
+{
+    pgprot_t PGProtFlags;
+    IMG_VOID *pvRet;
+    
+    if (!AllocFlagsToPGProt(&PGProtFlags, ui32AllocFlags))
+    {
+            return NULL;
+    }
+
+       /* Allocate virtually contiguous pages */
+    pvRet = __vmalloc(ui32Bytes, GFP_KERNEL | __GFP_HIGHMEM, PGProtFlags);
+    
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+    if (pvRet)
+    {
+        DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE_VMALLOC,
+                               pvRet,
+                               pvRet,
+                               0,
+                               NULL,
+                               PAGE_ALIGN(ui32Bytes),
+                               pszFileName,
+                               ui32Line
+                              );
+    }
+#else
+    PVR_UNREFERENCED_PARAMETER(pszFileName);
+    PVR_UNREFERENCED_PARAMETER(ui32Line);
+#endif
+
+    return pvRet;
+}
+
+
+IMG_VOID
+_VFreeWrapper(IMG_VOID *pvCpuVAddr, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
+{
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+    DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_VMALLOC, pvCpuVAddr, pszFileName, ui32Line);
+#else
+    PVR_UNREFERENCED_PARAMETER(pszFileName);
+    PVR_UNREFERENCED_PARAMETER(ui32Line);
+#endif
+    vfree(pvCpuVAddr);
+}
+
+
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+static IMG_VOID *
+_VMapWrapper(struct page **ppsPageList, IMG_UINT32 ui32NumPages, IMG_UINT32 ui32AllocFlags, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
+{
+    pgprot_t PGProtFlags;
+    IMG_VOID *pvRet;
+
+    if (!AllocFlagsToPGProt(&PGProtFlags, ui32AllocFlags))
+    {
+            return NULL;
+    }
+
+    pvRet = vmap(ppsPageList, ui32NumPages, GFP_KERNEL | __GFP_HIGHMEM, PGProtFlags);
+
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+    if (pvRet)
+    {
+        DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE_VMAP,
+                               pvRet,
+                               pvRet,
+                               0,
+                               NULL,
+                               PAGES_TO_BYTES(ui32NumPages),
+                               pszFileName,
+                               ui32Line
+                              );
+    }
+#else
+    PVR_UNREFERENCED_PARAMETER(pszFileName);
+    PVR_UNREFERENCED_PARAMETER(ui32Line);
+#endif
+
+    return pvRet;
+}
+
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+#define VMapWrapper(ppsPageList, ui32Bytes, ui32AllocFlags) _VMapWrapper(ppsPageList, ui32Bytes, ui32AllocFlags, __FILE__, __LINE__)
+#else
+#define VMapWrapper(ppsPageList, ui32Bytes, ui32AllocFlags) _VMapWrapper(ppsPageList, ui32Bytes, ui32AllocFlags, NULL, 0)
+#endif
+
+
+static IMG_VOID
+_VUnmapWrapper(IMG_VOID *pvCpuVAddr, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
+{
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+    DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_VMAP, pvCpuVAddr, pszFileName, ui32Line);
+#else
+    PVR_UNREFERENCED_PARAMETER(pszFileName);
+    PVR_UNREFERENCED_PARAMETER(ui32Line);
+#endif
+    vunmap(pvCpuVAddr);
+}
+
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+#define VUnmapWrapper(pvCpuVAddr) _VUnmapWrapper(pvCpuVAddr, __FILE__, __LINE__)
+#else
+#define VUnmapWrapper(pvCpuVAddr) _VUnmapWrapper(pvCpuVAddr, NULL, 0)
+#endif
+
+#endif /* defined(PVR_LINUX_MEM_AREA_USE_VMAP) */
+
+
+IMG_VOID
+_KMemCacheFreeWrapper(LinuxKMemCache *psCache, IMG_VOID *pvObject, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
+{
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+    DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE, pvObject, pszFileName, ui32Line);
+#else
+    PVR_UNREFERENCED_PARAMETER(pszFileName);
+    PVR_UNREFERENCED_PARAMETER(ui32Line);
+#endif
+
+    kmem_cache_free(psCache, pvObject);
+}
+
+
+const IMG_CHAR *
+KMemCacheNameWrapper(LinuxKMemCache *psCache)
+{
+    PVR_UNREFERENCED_PARAMETER(psCache);
+
+    /* In this case kmem_cache_t is an incomplete typedef,
+     * so we can't even de-reference to get the name member. It is also a GPL export symbol */
+    return "";
+}
+
+
+static LinuxPagePoolEntry *
+LinuxPagePoolEntryAlloc(IMG_VOID)
+{
+    return KMemCacheAllocWrapper(g_PsLinuxPagePoolCache, GFP_KERNEL);
+}
+
+static IMG_VOID
+LinuxPagePoolEntryFree(LinuxPagePoolEntry *psPagePoolEntry)
+{
+       KMemCacheFreeWrapper(g_PsLinuxPagePoolCache, psPagePoolEntry);
+}
+
+
+static struct page *
+AllocPageFromLinux(void)
+{
+       struct page *psPage;
+
+        psPage = alloc_pages(GFP_KERNEL | __GFP_HIGHMEM, 0);
+        if (!psPage)
+        {
+            return NULL;
+
+        }
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15))
+       /* Reserve those pages to allow them to be re-mapped to user space */
+#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0))               
+       SetPageReserved(psPage);
+#else
+        mem_map_reserve(psPage);
+#endif
+#endif
+       return psPage;
+}
+
+
+static IMG_VOID
+FreePageToLinux(struct page *psPage)
+{
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15))              
+#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0))               
+        ClearPageReserved(psPage);
+#else
+        mem_map_reserve(psPage);
+#endif         
+#endif 
+        __free_pages(psPage, 0);
+}
+
+
+#if (PVR_LINUX_MEM_AREA_POOL_MAX_PAGES != 0)
+static DEFINE_MUTEX(g_sPagePoolMutex);
+
+static inline void
+PagePoolLock(void)
+{
+       mutex_lock(&g_sPagePoolMutex);
+}
+
+static inline void
+PagePoolUnlock(void)
+{
+       mutex_unlock(&g_sPagePoolMutex);
+}
+
+static inline int
+PagePoolTrylock(void)
+{
+       return mutex_trylock(&g_sPagePoolMutex);
+}
+
+#else  /* (PVR_LINUX_MEM_AREA_POOL_MAX_PAGES != 0) */
+static inline void
+PagePoolLock(void)
+{
+}
+
+static inline void
+PagePoolUnlock(void)
+{
+}
+
+static inline int
+PagePoolTrylock(void)
+{
+       return 1;
+}
+#endif /* (PVR_LINUX_MEM_AREA_POOL_MAX_PAGES != 0) */
+
+
+static inline void
+AddEntryToPool(LinuxPagePoolEntry *psPagePoolEntry)
+{
+       list_add_tail(&psPagePoolEntry->sPagePoolItem, &g_sPagePoolList);
+       atomic_inc(&g_sPagePoolEntryCount);
+}
+
+static inline void
+RemoveEntryFromPool(LinuxPagePoolEntry *psPagePoolEntry)
+{
+       list_del(&psPagePoolEntry->sPagePoolItem);
+       atomic_dec(&g_sPagePoolEntryCount);
+}
+
+static inline LinuxPagePoolEntry *
+RemoveFirstEntryFromPool(void)
+{
+       LinuxPagePoolEntry *psPagePoolEntry;
+
+       if (list_empty(&g_sPagePoolList))
+       {
+               PVR_ASSERT(atomic_read(&g_sPagePoolEntryCount) == 0);
+
+               return NULL;
+       }
+
+       PVR_ASSERT(atomic_read(&g_sPagePoolEntryCount) > 0);
+
+       psPagePoolEntry = list_first_entry(&g_sPagePoolList, LinuxPagePoolEntry, sPagePoolItem);
+
+       RemoveEntryFromPool(psPagePoolEntry);
+
+       return psPagePoolEntry;
+}
+
+static struct page *
+AllocPage(IMG_UINT32 ui32AreaFlags, IMG_BOOL *pbFromPagePool)
+{
+       struct page *psPage = NULL;
+
+       /*
+        * Only uncached allocations can come from the page pool.
+        * The page pool is currently used to reduce the cost of
+        * invalidating the CPU cache when uncached memory is allocated.
+        */
+       if (AreaIsUncached(ui32AreaFlags) && atomic_read(&g_sPagePoolEntryCount) != 0)
+       {
+               LinuxPagePoolEntry *psPagePoolEntry;
+
+               PagePoolLock();
+               psPagePoolEntry = RemoveFirstEntryFromPool();
+               PagePoolUnlock();
+
+               /* List may have changed since we checked the counter */
+               if (psPagePoolEntry)
                {
-                       g_SysRAMWaterMark -= psCurrentRecord->ui32Bytes;
+                       psPage = psPagePoolEntry->psPage;
+                       LinuxPagePoolEntryFree(psPagePoolEntry);
+                       *pbFromPagePool = IMG_TRUE;
                }
-               else if(eAllocType == DEBUG_MEM_ALLOC_TYPE_IOREMAP
-                               || eAllocType == DEBUG_MEM_ALLOC_TYPE_IO)
+       }
+
+       if (!psPage)
+       {
+               psPage = AllocPageFromLinux();
+               if (psPage)
                {
-                       g_IOMemWaterMark -= psCurrentRecord->ui32Bytes;
+                       *pbFromPagePool = IMG_FALSE;
                }
-               
-               List_DEBUG_MEM_ALLOC_REC_Remove(psCurrentRecord);
-               kfree(psCurrentRecord);
-
-               return IMG_TRUE;
        }
-       else
+
+       return psPage;
+
+}
+
+static IMG_VOID
+FreePage(IMG_BOOL bToPagePool, struct page *psPage)
+{
+       /* Only uncached allocations can be freed to the page pool */
+       if (bToPagePool && atomic_read(&g_sPagePoolEntryCount) < g_iPagePoolMaxEntries)
        {
-               return IMG_FALSE;
+               LinuxPagePoolEntry *psPagePoolEntry = LinuxPagePoolEntryAlloc();
+               if (psPagePoolEntry)
+               {
+                       psPagePoolEntry->psPage = psPage;
+
+                       PagePoolLock();
+                       AddEntryToPool(psPagePoolEntry);
+                       PagePoolUnlock();
+
+                       return;
+               }
        }
-}
 
+       FreePageToLinux(psPage);
+}
 
 static IMG_VOID
-DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE eAllocType, IMG_VOID *pvKey, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
+FreePagePool(IMG_VOID)
 {
-    LinuxLockMutex(&g_sDebugMutex);
+       LinuxPagePoolEntry *psPagePoolEntry, *psTempPoolEntry;
 
-    
-       if(!List_DEBUG_MEM_ALLOC_REC_IMG_BOOL_Any_va(g_MemoryRecords,
-                                                                                               DebugMemAllocRecordRemove_AnyVaCb,
-                                                                                               eAllocType,
-                                                                                               pvKey))
+       PagePoolLock();
+
+#if (PVR_LINUX_MEM_AREA_POOL_MAX_PAGES != 0)
+       PVR_TRACE(("%s: Freeing %d pages from pool", __FUNCTION__, atomic_read(&g_sPagePoolEntryCount)));
+#else
+       PVR_ASSERT(atomic_read(&g_sPagePoolEntryCount) == 0);
+       PVR_ASSERT(list_empty(&g_sPagePoolList));
+#endif
+
+       list_for_each_entry_safe(psPagePoolEntry, psTempPoolEntry, &g_sPagePoolList, sPagePoolItem)
        {
-               PVR_DPF((PVR_DBG_ERROR, "%s: couldn't find an entry for type=%s with pvKey=%p (called from %s, line %d\n",
-               __FUNCTION__, DebugMemAllocRecordTypeToString(eAllocType), pvKey,
-               pszFileName, ui32Line));
+               RemoveEntryFromPool(psPagePoolEntry);
+
+               FreePageToLinux(psPagePoolEntry->psPage);
+               LinuxPagePoolEntryFree(psPagePoolEntry);
        }
 
-    LinuxUnLockMutex(&g_sDebugMutex);
+       PVR_ASSERT(atomic_read(&g_sPagePoolEntryCount) == 0);
+
+       PagePoolUnlock();
 }
 
+#if defined(PVR_LINUX_MEM_AREA_POOL_ALLOW_SHRINK)
+#if defined(PVRSRV_NEED_PVR_ASSERT)
+static struct shrinker g_sShrinker;
+#endif
 
-static IMG_CHAR *
-DebugMemAllocRecordTypeToString(DEBUG_MEM_ALLOC_TYPE eAllocType)
+static int
+ShrinkPagePool(struct shrinker *psShrinker, struct shrink_control *psShrinkControl)
 {
-    IMG_CHAR *apszDebugMemoryRecordTypes[] = {
-        "KMALLOC",
-        "VMALLOC",
-        "ALLOC_PAGES",
-        "IOREMAP",
-        "IO",
-        "KMEM_CACHE_ALLOC"
-    };
-    return apszDebugMemoryRecordTypes[eAllocType];
-}
-#endif
+       unsigned long uNumToScan = psShrinkControl->nr_to_scan;
 
+       PVR_ASSERT(psShrinker == &g_sShrinker);
+       (void)psShrinker;
 
+       if (uNumToScan != 0)
+       {
+               LinuxPagePoolEntry *psPagePoolEntry, *psTempPoolEntry;
 
-IMG_VOID *
-_VMallocWrapper(IMG_UINT32 ui32Bytes,
-                IMG_UINT32 ui32AllocFlags,
-                IMG_CHAR *pszFileName,
-                IMG_UINT32 ui32Line)
+               PVR_TRACE(("%s: Number to scan: %ld", __FUNCTION__, uNumToScan));
+               PVR_TRACE(("%s: Pages in pool before scan: %d", __FUNCTION__, atomic_read(&g_sPagePoolEntryCount)));
+
+               if (!PagePoolTrylock())
+               {
+                       PVR_TRACE(("%s: Couldn't get page pool lock", __FUNCTION__));
+                       return -1;
+               }
+
+               list_for_each_entry_safe(psPagePoolEntry, psTempPoolEntry, &g_sPagePoolList, sPagePoolItem)
+               {
+                       RemoveEntryFromPool(psPagePoolEntry);
+
+                       FreePageToLinux(psPagePoolEntry->psPage);
+                       LinuxPagePoolEntryFree(psPagePoolEntry);
+
+                       if (--uNumToScan == 0)
+                       {
+                               break;
+                       }
+               }
+
+               if (list_empty(&g_sPagePoolList))
+               {
+                       PVR_ASSERT(atomic_read(&g_sPagePoolEntryCount) == 0);
+               }
+
+               PagePoolUnlock();
+
+               PVR_TRACE(("%s: Pages in pool after scan: %d", __FUNCTION__, atomic_read(&g_sPagePoolEntryCount)));
+       }
+
+       return atomic_read(&g_sPagePoolEntryCount);
+}
+#endif
+
+static IMG_BOOL
+AllocPages(IMG_UINT32 ui32AreaFlags, struct page ***pppsPageList, IMG_HANDLE *phBlockPageList, IMG_UINT32 ui32NumPages, IMG_BOOL *pbFromPagePool)
 {
-    pgprot_t PGProtFlags;
-    IMG_VOID *pvRet;
+    struct page **ppsPageList;
+    IMG_HANDLE hBlockPageList;
+    IMG_INT32 i;               /* Must be signed; see "for" loop conditions */
+    PVRSRV_ERROR eError;
+    IMG_BOOL bFromPagePool = IMG_FALSE;
+
+    eError = OSAllocMem(0, sizeof(*ppsPageList) * ui32NumPages, (IMG_VOID **)&ppsPageList, &hBlockPageList,
+                                                       "Array of pages");
+    if (eError != PVRSRV_OK)
+    {
+        goto failed_page_list_alloc;
+    }
     
-    switch(ui32AllocFlags & PVRSRV_HAP_CACHETYPE_MASK)
+    *pbFromPagePool = IMG_TRUE;
+    for(i = 0; i < (IMG_INT32)ui32NumPages; i++)
     {
-        case PVRSRV_HAP_CACHED:
-            PGProtFlags = PAGE_KERNEL;
-            break;
-        case PVRSRV_HAP_WRITECOMBINE:
-            PGProtFlags = PGPROT_WC(PAGE_KERNEL);
-            break;
-        case PVRSRV_HAP_UNCACHED:
-            PGProtFlags = PGPROT_UC(PAGE_KERNEL);
-            break;
-        default:
-            PVR_DPF((PVR_DBG_ERROR,
-                     "VMAllocWrapper: unknown mapping flags=0x%08x",
-                     ui32AllocFlags));
-            dump_stack();
-            return NULL;
+        ppsPageList[i] = AllocPage(ui32AreaFlags, &bFromPagePool);
+        if (!ppsPageList[i])
+        {
+            goto failed_alloc_pages;
+        }
+       *pbFromPagePool &= bFromPagePool;
     }
 
-       
-    pvRet = __vmalloc(ui32Bytes, GFP_KERNEL | __GFP_HIGHMEM, PGProtFlags);
-    
+    *pppsPageList = ppsPageList;
+    *phBlockPageList = hBlockPageList;
+
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    if(pvRet)
+    DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES,
+                           ppsPageList,
+                           0,
+                           0,
+                           NULL,
+                           PAGES_TO_BYTES(ui32NumPages),
+                           "unknown",
+                           0
+                          );
+#endif
+
+    return IMG_TRUE;
+    
+failed_alloc_pages:
+    for(i--; i >= 0; i--)
     {
-        DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE_VMALLOC,
-                               pvRet,
-                               pvRet,
-                               0,
-                               NULL,
-                               PAGE_ALIGN(ui32Bytes),
-                               pszFileName,
-                               ui32Line
-                               );
+        FreePage(*pbFromPagePool, ppsPageList[i]);
     }
-#else
-    PVR_UNREFERENCED_PARAMETER(pszFileName);
-    PVR_UNREFERENCED_PARAMETER(ui32Line);
-#endif
+    (IMG_VOID) OSFreeMem(0, sizeof(*ppsPageList) * ui32NumPages, ppsPageList, hBlockPageList);
 
-    return pvRet;
+failed_page_list_alloc:
+    return IMG_FALSE;
 }
 
 
-IMG_VOID
-_VFreeWrapper(IMG_VOID *pvCpuVAddr, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
+static IMG_VOID
+FreePages(IMG_BOOL bToPagePool, struct page **ppsPageList, IMG_HANDLE hBlockPageList, IMG_UINT32 ui32NumPages)
 {
+    IMG_INT32 i;
+
+    for(i = 0; i < (IMG_INT32)ui32NumPages; i++)
+    {
+        FreePage(bToPagePool, ppsPageList[i]);
+    }
+
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_VMALLOC, pvCpuVAddr, pszFileName, ui32Line);
-#else
-    PVR_UNREFERENCED_PARAMETER(pszFileName);
-    PVR_UNREFERENCED_PARAMETER(ui32Line);
+    DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES, ppsPageList, __FILE__, __LINE__);
 #endif
-    vfree(pvCpuVAddr);
+
+    (IMG_VOID) OSFreeMem(0, sizeof(*ppsPageList) * ui32NumPages, ppsPageList, hBlockPageList);
 }
 
 
 LinuxMemArea *
 NewVMallocLinuxMemArea(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags)
 {
-    LinuxMemArea *psLinuxMemArea;
+    LinuxMemArea *psLinuxMemArea = NULL;
     IMG_VOID *pvCpuVAddr;
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+    IMG_UINT32 ui32NumPages = 0;
+    struct page **ppsPageList = NULL;
+    IMG_HANDLE hBlockPageList;
+#endif
+    IMG_BOOL bFromPagePool = IMG_FALSE;
 
     psLinuxMemArea = LinuxMemAreaStructAlloc();
-    if(!psLinuxMemArea)
+    if (!psLinuxMemArea)
     {
         goto failed;
     }
 
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+    ui32NumPages = RANGE_TO_PAGES(ui32Bytes);
+
+    if (!AllocPages(ui32AreaFlags, &ppsPageList, &hBlockPageList, ui32NumPages, &bFromPagePool))
+    {
+       goto failed;
+    }
+
+    pvCpuVAddr = VMapWrapper(ppsPageList, ui32NumPages, ui32AreaFlags);
+#else  /* defined(PVR_LINUX_MEM_AREA_USE_VMAP) */
     pvCpuVAddr = VMallocWrapper(ui32Bytes, ui32AreaFlags);
-    if(!pvCpuVAddr)
+    if (!pvCpuVAddr)
     {
         goto failed;
     }
-    
+/* PG_reserved was deprecated in linux-2.6.15 */
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15))
-    
+    /* Reserve those pages to allow them to be re-mapped to user space */
     ReservePages(pvCpuVAddr, ui32Bytes);
 #endif
+#endif /* defined(PVR_LINUX_MEM_AREA_USE_VMAP) */ 
 
     psLinuxMemArea->eAreaType = LINUX_MEM_AREA_VMALLOC;
     psLinuxMemArea->uData.sVmalloc.pvVmallocAddress = pvCpuVAddr;
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+    psLinuxMemArea->uData.sVmalloc.ppsPageList = ppsPageList;
+    psLinuxMemArea->uData.sVmalloc.hBlockPageList = hBlockPageList;
+#endif
     psLinuxMemArea->ui32ByteSize = ui32Bytes;
     psLinuxMemArea->ui32AreaFlags = ui32AreaFlags;
     INIT_LIST_HEAD(&psLinuxMemArea->sMMapOffsetStructList);
@@ -611,16 +1004,41 @@ NewVMallocLinuxMemArea(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags)
     DebugLinuxMemAreaRecordAdd(psLinuxMemArea, ui32AreaFlags);
 #endif
 
-    
-    if(ui32AreaFlags & (PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_UNCACHED))
-        OSInvalidateCPUCacheRangeKM(psLinuxMemArea, pvCpuVAddr, ui32Bytes);
+    /* This works around a problem where Linux will not invalidate
+     * the cache for physical memory it frees that is direct mapped.
+     *
+     * As a result, cache entries remain that may be subsequently flushed
+     * to these physical pages after they have been allocated for another
+     * purpose. For a subsequent cached use of this memory, that is not a
+     * problem, but if we are allocating uncached or write-combined memory,
+     * and bypassing the cache, it can cause subsequent uncached writes to
+     * the memory to be replaced with junk from the cache.
+     *
+     * If the pages are from our page cache, no cache invalidate is needed.
+     *
+     * This just handles the __vmalloc() case (when we have a kernel virtual
+     * address range). The alloc_pages() path is handled in mmap.c.
+     */
+    if (AreaIsUncached(ui32AreaFlags) && !bFromPagePool)
+    {
+        OSInvalidateCPUCacheRangeKM(psLinuxMemArea, 0, pvCpuVAddr, ui32Bytes);
+    }
 
     return psLinuxMemArea;
 
 failed:
     PVR_DPF((PVR_DBG_ERROR, "%s: failed!", __FUNCTION__));
-    if(psLinuxMemArea)
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+    if (ppsPageList)
+    {
+       FreePages(bFromPagePool, ppsPageList, hBlockPageList, ui32NumPages);
+    }
+#endif
+    if (psLinuxMemArea)
+    {
         LinuxMemAreaStructFree(psLinuxMemArea);
+    }
+
     return NULL;
 }
 
@@ -628,6 +1046,12 @@ failed:
 IMG_VOID
 FreeVMallocLinuxMemArea(LinuxMemArea *psLinuxMemArea)
 {
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+    IMG_UINT32 ui32NumPages;
+    struct page **ppsPageList;
+    IMG_HANDLE hBlockPageList;
+#endif
+
     PVR_ASSERT(psLinuxMemArea);
     PVR_ASSERT(psLinuxMemArea->eAreaType == LINUX_MEM_AREA_VMALLOC);
     PVR_ASSERT(psLinuxMemArea->uData.sVmalloc.pvVmallocAddress);
@@ -636,20 +1060,34 @@ FreeVMallocLinuxMemArea(LinuxMemArea *psLinuxMemArea)
     DebugLinuxMemAreaRecordRemove(psLinuxMemArea);
 #endif
 
+    PVR_DPF((PVR_DBG_MESSAGE,"%s: pvCpuVAddr: %p",
+             __FUNCTION__, psLinuxMemArea->uData.sVmalloc.pvVmallocAddress));
+
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+    VUnmapWrapper(psLinuxMemArea->uData.sVmalloc.pvVmallocAddress);
+
+    ui32NumPages = RANGE_TO_PAGES(psLinuxMemArea->ui32ByteSize);
+    ppsPageList = psLinuxMemArea->uData.sVmalloc.ppsPageList;
+    hBlockPageList = psLinuxMemArea->uData.sVmalloc.hBlockPageList;
+    
+    FreePages(CanFreeToPool(psLinuxMemArea), ppsPageList, hBlockPageList, ui32NumPages);
+#else
+/* PG_reserved was deprecated in linux-2.6.15 */
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15))
-       UnreservePages(psLinuxMemArea->uData.sVmalloc.pvVmallocAddress,
+    UnreservePages(psLinuxMemArea->uData.sVmalloc.pvVmallocAddress,
                     psLinuxMemArea->ui32ByteSize);
 #endif
 
-    PVR_DPF((PVR_DBG_MESSAGE,"%s: pvCpuVAddr: %p",
-             __FUNCTION__, psLinuxMemArea->uData.sVmalloc.pvVmallocAddress));
     VFreeWrapper(psLinuxMemArea->uData.sVmalloc.pvVmallocAddress);
+#endif /* defined(PVR_LINUX_MEM_AREA_USE_VMAP) */ 
 
     LinuxMemAreaStructFree(psLinuxMemArea);
 }
 
 
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15))
+/* Reserve pages of memory in order that they're not automatically
+   deallocated after the last user reference dies. */
 static IMG_VOID
 ReservePages(IMG_VOID *pvAddress, IMG_UINT32 ui32Length)
 {
@@ -667,6 +1105,7 @@ ReservePages(IMG_VOID *pvAddress, IMG_UINT32 ui32Length)
 }
 
 
+/* Un-reserve pages of memory in order that they can be freed. */
 static IMG_VOID
 UnreservePages(IMG_VOID *pvAddress, IMG_UINT32 ui32Length)
 {
@@ -682,7 +1121,7 @@ UnreservePages(IMG_VOID *pvAddress, IMG_UINT32 ui32Length)
 #endif
        }
 }
-#endif 
+#endif /* (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15)) */
 
 
 IMG_VOID *
@@ -694,7 +1133,7 @@ _IORemapWrapper(IMG_CPU_PHYADDR BasePAddr,
 {
     IMG_VOID *pvIORemapCookie;
     
-    switch(ui32MappingFlags & PVRSRV_HAP_CACHETYPE_MASK)
+    switch (ui32MappingFlags & PVRSRV_HAP_CACHETYPE_MASK)
     {
         case PVRSRV_HAP_CACHED:
            pvIORemapCookie = (IMG_VOID *)IOREMAP(BasePAddr.uiAddr, ui32Bytes);
@@ -711,7 +1150,7 @@ _IORemapWrapper(IMG_CPU_PHYADDR BasePAddr,
     }
     
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    if(pvIORemapCookie)
+    if (pvIORemapCookie)
     {
         DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE_IOREMAP,
                                pvIORemapCookie,
@@ -721,7 +1160,7 @@ _IORemapWrapper(IMG_CPU_PHYADDR BasePAddr,
                                ui32Bytes,
                                pszFileName,
                                ui32Line
-                               );
+                              );
     }
 #else
     PVR_UNREFERENCED_PARAMETER(pszFileName);
@@ -754,13 +1193,13 @@ NewIORemapLinuxMemArea(IMG_CPU_PHYADDR BasePAddr,
     IMG_VOID *pvIORemapCookie;
 
     psLinuxMemArea = LinuxMemAreaStructAlloc();
-    if(!psLinuxMemArea)
+    if (!psLinuxMemArea)
     {
         return NULL;
     }
 
     pvIORemapCookie = IORemapWrapper(BasePAddr, ui32Bytes, ui32AreaFlags);
-    if(!pvIORemapCookie)
+    if (!pvIORemapCookie)
     {
         LinuxMemAreaStructFree(psLinuxMemArea);
         return NULL;
@@ -797,6 +1236,16 @@ FreeIORemapLinuxMemArea(LinuxMemArea *psLinuxMemArea)
 
 
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
+/*
+ * Avoid using remap_pfn_range on RAM, if possible.  On x86 systems, with
+ * PAT enabled, remap_pfn_range checks the page attributes requested by 
+ * remap_pfn_range against those of the direct kernel mapping for those
+ * pages (if any).  This is rather annoying if the pages have been obtained
+ * with alloc_pages, where we just ask for raw pages; we don't care about
+ * the direct mapping.  This latter issue arises when device memory is
+ * exported from one process to another.  Services implements this
+ * using memory wrapping, which ends up creating an external KV memory area.
+ */
 static IMG_BOOL
 TreatExternalPagesAsContiguous(IMG_SYS_PHYADDR *psSysPhysAddr, IMG_UINT32 ui32Bytes, IMG_BOOL bPhysContig)
 {
@@ -804,7 +1253,10 @@ TreatExternalPagesAsContiguous(IMG_SYS_PHYADDR *psSysPhysAddr, IMG_UINT32 ui32By
        IMG_UINT32 ui32AddrChk;
        IMG_UINT32 ui32NumPages = RANGE_TO_PAGES(ui32Bytes);
 
-       
+       /*
+        * If bPhysContig is IMG_TRUE, we must assume psSysPhysAddr points
+        * to the address of the first page, not an array of page addresses.
+        */
        for (ui32 = 0, ui32AddrChk = psSysPhysAddr[0].uiAddr;
                ui32 < ui32NumPages;
                ui32++, ui32AddrChk = (bPhysContig) ? (ui32AddrChk + PAGE_SIZE) : psSysPhysAddr[ui32].uiAddr)
@@ -841,7 +1293,7 @@ LinuxMemArea *NewExternalKVLinuxMemArea(IMG_SYS_PHYADDR *pBasePAddr, IMG_VOID *p
     LinuxMemArea *psLinuxMemArea;
 
     psLinuxMemArea = LinuxMemAreaStructAlloc();
-    if(!psLinuxMemArea)
+    if (!psLinuxMemArea)
     {
         return NULL;
     }
@@ -894,12 +1346,12 @@ NewIOLinuxMemArea(IMG_CPU_PHYADDR BasePAddr,
                   IMG_UINT32 ui32AreaFlags)
 {
     LinuxMemArea *psLinuxMemArea = LinuxMemAreaStructAlloc();
-    if(!psLinuxMemArea)
+    if (!psLinuxMemArea)
     {
         return NULL;
     }
 
-    
+    /* Nothing to activly do. We just keep a record of the physical range. */
     psLinuxMemArea->eAreaType = LINUX_MEM_AREA_IO;
     psLinuxMemArea->uData.sIO.CPUPhysAddr.uiAddr = BasePAddr.uiAddr;
     psLinuxMemArea->ui32ByteSize = ui32Bytes;
@@ -915,7 +1367,7 @@ NewIOLinuxMemArea(IMG_CPU_PHYADDR BasePAddr,
                            ui32Bytes,
                            "unknown",
                            0
-                           );
+                          );
 #endif
    
 #if defined(DEBUG_LINUX_MEM_AREAS)
@@ -940,7 +1392,7 @@ FreeIOLinuxMemArea(LinuxMemArea *psLinuxMemArea)
                               (IMG_VOID *)psLinuxMemArea->uData.sIO.CPUPhysAddr.uiAddr, __FILE__, __LINE__);
 #endif
 
-    
+    /* Nothing more to do than free the LinuxMemArea struct */
 
     LinuxMemAreaStructFree(psLinuxMemArea);
 }
@@ -950,132 +1402,219 @@ LinuxMemArea *
 NewAllocPagesLinuxMemArea(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags)
 {
     LinuxMemArea *psLinuxMemArea;
-    IMG_UINT32 ui32PageCount;
-    struct page **pvPageList;
+    IMG_UINT32 ui32NumPages;
+    struct page **ppsPageList;
     IMG_HANDLE hBlockPageList;
-    IMG_INT32 i;               
-    PVRSRV_ERROR eError;
-    
+    IMG_BOOL bFromPagePool;
+
     psLinuxMemArea = LinuxMemAreaStructAlloc();
-    if(!psLinuxMemArea)
+    if (!psLinuxMemArea)
     {
         goto failed_area_alloc;
     }
     
-    ui32PageCount = RANGE_TO_PAGES(ui32Bytes);
-    eError = OSAllocMem(0, sizeof(*pvPageList) * ui32PageCount, (IMG_VOID **)&pvPageList, &hBlockPageList,
-                                                       "Array of pages");
-    if(eError != PVRSRV_OK)
+    ui32NumPages = RANGE_TO_PAGES(ui32Bytes);
+
+    if (!AllocPages(ui32AreaFlags, &ppsPageList, &hBlockPageList, ui32NumPages, &bFromPagePool))
     {
-        goto failed_page_list_alloc;
+       goto failed_alloc_pages;
     }
+
+    psLinuxMemArea->eAreaType = LINUX_MEM_AREA_ALLOC_PAGES;
+    psLinuxMemArea->uData.sPageList.ppsPageList = ppsPageList;
+    psLinuxMemArea->uData.sPageList.hBlockPageList = hBlockPageList;
+    psLinuxMemArea->ui32ByteSize = ui32Bytes;
+    psLinuxMemArea->ui32AreaFlags = ui32AreaFlags;
+    INIT_LIST_HEAD(&psLinuxMemArea->sMMapOffsetStructList);
+
+    /* We defer the cache flush to the first user mapping of this memory */
+    psLinuxMemArea->bNeedsCacheInvalidate = AreaIsUncached(ui32AreaFlags) && !bFromPagePool;
+
+#if defined(DEBUG_LINUX_MEM_AREAS)
+    DebugLinuxMemAreaRecordAdd(psLinuxMemArea, ui32AreaFlags);
+#endif
+
+    return psLinuxMemArea;
+    
+failed_alloc_pages:
+    LinuxMemAreaStructFree(psLinuxMemArea);
+failed_area_alloc:
+    PVR_DPF((PVR_DBG_ERROR, "%s: failed", __FUNCTION__));
+    
+    return NULL;
+}
+
+
+IMG_VOID
+FreeAllocPagesLinuxMemArea(LinuxMemArea *psLinuxMemArea)
+{
+    IMG_UINT32 ui32NumPages;
+    struct page **ppsPageList;
+    IMG_HANDLE hBlockPageList;
+
+    PVR_ASSERT(psLinuxMemArea);
+    PVR_ASSERT(psLinuxMemArea->eAreaType == LINUX_MEM_AREA_ALLOC_PAGES);
+
+#if defined(DEBUG_LINUX_MEM_AREAS)
+    DebugLinuxMemAreaRecordRemove(psLinuxMemArea);
+#endif
+    
+    ui32NumPages = RANGE_TO_PAGES(psLinuxMemArea->ui32ByteSize);
+    ppsPageList = psLinuxMemArea->uData.sPageList.ppsPageList;
+    hBlockPageList = psLinuxMemArea->uData.sPageList.hBlockPageList;
     
-    for(i=0; i<(IMG_INT32)ui32PageCount; i++)
+    FreePages(CanFreeToPool(psLinuxMemArea), ppsPageList, hBlockPageList, ui32NumPages);
+  
+    LinuxMemAreaStructFree(psLinuxMemArea);
+}
+
+#if defined(CONFIG_ION_OMAP)
+
+#include "env_perproc.h"
+
+#include <linux/ion.h>
+#include <linux/omap_ion.h>
+
+extern struct ion_client *gpsIONClient;
+
+LinuxMemArea *
+NewIONLinuxMemArea(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags,
+                   IMG_PVOID pvPrivData, IMG_UINT32 ui32PrivDataLength)
+{
+    const IMG_UINT32 ui32AllocDataLen =
+        offsetof(struct omap_ion_tiler_alloc_data, handle);
+    struct omap_ion_tiler_alloc_data asAllocData[2] = {};
+    u32 *pu32PageAddrs[2] = { NULL, NULL };
+    IMG_UINT32 i, ui32NumHandlesPerFd;
+    IMG_BYTE *pbPrivData = pvPrivData;
+       IMG_CPU_PHYADDR *pCPUPhysAddrs;
+    int iNumPages[2] = { 0, 0 };
+    LinuxMemArea *psLinuxMemArea;
+
+    psLinuxMemArea = LinuxMemAreaStructAlloc();
+    if (!psLinuxMemArea)
+    {
+        PVR_DPF((PVR_DBG_ERROR, "%s: Failed to allocate LinuxMemArea struct", __func__));
+        goto err_out;
+    }
+
+    /* Depending on the UM config, userspace might give us info for
+     * one or two ION allocations. Divide the total size of data we
+     * were given by this ui32AllocDataLen, and check it's 1 or 2.
+     * Otherwise abort.
+     */
+    BUG_ON(ui32PrivDataLength != ui32AllocDataLen &&
+           ui32PrivDataLength != ui32AllocDataLen * 2);
+    ui32NumHandlesPerFd = ui32PrivDataLength / ui32AllocDataLen;
+
+    /* Shuffle the alloc data into separate Y & UV bits and
+     * make two separate allocations via the tiler.
+     */
+    for(i = 0; i < ui32NumHandlesPerFd; i++)
     {
-        pvPageList[i] = alloc_pages(GFP_KERNEL | __GFP_HIGHMEM, 0);
-        if(!pvPageList[i])
+           memcpy(&asAllocData[i], &pbPrivData[i * ui32AllocDataLen], ui32AllocDataLen);
+
+        if (omap_ion_tiler_alloc(gpsIONClient, &asAllocData[i]) < 0)
         {
-            goto failed_alloc_pages;
-        }
-#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15))
-       
-#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0))               
-       SetPageReserved(pvPageList[i]);
-#else
-        mem_map_reserve(pvPageList[i]);
-#endif
-#endif
+            PVR_DPF((PVR_DBG_ERROR, "%s: Failed to allocate via ion_tiler", __func__));
+            goto err_free;
+        }
+
+        if (omap_tiler_pages(gpsIONClient, asAllocData[i].handle, &iNumPages[i],
+                            &pu32PageAddrs[i]) < 0)
+        {
+            PVR_DPF((PVR_DBG_ERROR, "%s: Failed to compute tiler pages", __func__));
+            goto err_free;
+        }
+    }
+
+    /* Assume the user-allocator has already done the tiler math and that the
+     * number of tiler pages allocated matches any other allocation type.
+     */
+    BUG_ON(ui32Bytes != (iNumPages[0] + iNumPages[1]) * PAGE_SIZE);
+    BUG_ON(sizeof(IMG_CPU_PHYADDR) != sizeof(int));
 
+    /* Glue the page lists together */
+    pCPUPhysAddrs = vmalloc(sizeof(IMG_CPU_PHYADDR) * (iNumPages[0] + iNumPages[1]));
+    if (!pCPUPhysAddrs)
+    {
+        PVR_DPF((PVR_DBG_ERROR, "%s: Failed to allocate page list", __func__));
+        goto err_free;
     }
+    for(i = 0; i < iNumPages[0]; i++)
+        pCPUPhysAddrs[i].uiAddr = pu32PageAddrs[0][i];
+    for(i = 0; i < iNumPages[1]; i++)
+        pCPUPhysAddrs[iNumPages[0] + i].uiAddr = pu32PageAddrs[1][i];
 
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES,
-                           pvPageList,
+    DebugMemAllocRecordAdd(DEBUG_MEM_ALLOC_TYPE_ION,
+                           asAllocData[0].handle,
                            0,
                            0,
                            NULL,
                            PAGE_ALIGN(ui32Bytes),
                            "unknown",
                            0
-                           );
+                          );
 #endif
 
-    psLinuxMemArea->eAreaType = LINUX_MEM_AREA_ALLOC_PAGES;
-    psLinuxMemArea->uData.sPageList.pvPageList = pvPageList;
-    psLinuxMemArea->uData.sPageList.hBlockPageList = hBlockPageList;
+    for(i = 0; i < 2; i++)
+        psLinuxMemArea->uData.sIONTilerAlloc.psIONHandle[i] = asAllocData[i].handle;
+
+    psLinuxMemArea->eAreaType = LINUX_MEM_AREA_ION;
+    psLinuxMemArea->uData.sIONTilerAlloc.pCPUPhysAddrs = pCPUPhysAddrs;
     psLinuxMemArea->ui32ByteSize = ui32Bytes;
     psLinuxMemArea->ui32AreaFlags = ui32AreaFlags;
     INIT_LIST_HEAD(&psLinuxMemArea->sMMapOffsetStructList);
 
-    
-    if(ui32AreaFlags & (PVRSRV_HAP_WRITECOMBINE | PVRSRV_HAP_UNCACHED))
-    {
-        psLinuxMemArea->bNeedsCacheInvalidate = IMG_TRUE;
-    }
+    /* We defer the cache flush to the first user mapping of this memory */
+    psLinuxMemArea->bNeedsCacheInvalidate = AreaIsUncached(ui32AreaFlags);
 
 #if defined(DEBUG_LINUX_MEM_AREAS)
     DebugLinuxMemAreaRecordAdd(psLinuxMemArea, ui32AreaFlags);
 #endif
 
+err_out:
     return psLinuxMemArea;
-    
-failed_alloc_pages:
-    for(i--; i >= 0; i--)
-    {
-        __free_pages(pvPageList[i], 0);
-    }
-    (IMG_VOID) OSFreeMem(0, sizeof(*pvPageList) * ui32PageCount, pvPageList, hBlockPageList);
-       psLinuxMemArea->uData.sPageList.pvPageList = IMG_NULL; 
-failed_page_list_alloc:
+
+err_free:
     LinuxMemAreaStructFree(psLinuxMemArea);
-failed_area_alloc:
-    PVR_DPF((PVR_DBG_ERROR, "%s: failed", __FUNCTION__));
-    
-    return NULL;
+    psLinuxMemArea = IMG_NULL;
+    goto err_out;
 }
 
 
 IMG_VOID
-FreeAllocPagesLinuxMemArea(LinuxMemArea *psLinuxMemArea)
+FreeIONLinuxMemArea(LinuxMemArea *psLinuxMemArea)
 {
-    IMG_UINT32 ui32PageCount;
-    struct page **pvPageList;
-    IMG_HANDLE hBlockPageList;
-    IMG_INT32 i;
-
-    PVR_ASSERT(psLinuxMemArea);
-    PVR_ASSERT(psLinuxMemArea->eAreaType == LINUX_MEM_AREA_ALLOC_PAGES);
+    IMG_UINT32 i;
 
 #if defined(DEBUG_LINUX_MEM_AREAS)
     DebugLinuxMemAreaRecordRemove(psLinuxMemArea);
 #endif
-    
-    ui32PageCount = RANGE_TO_PAGES(psLinuxMemArea->ui32ByteSize);
-    pvPageList = psLinuxMemArea->uData.sPageList.pvPageList;
-    hBlockPageList = psLinuxMemArea->uData.sPageList.hBlockPageList;
-    
+
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES, pvPageList, __FILE__, __LINE__);
+    DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_ION,
+                              psLinuxMemArea->uData.sIONTilerAlloc.psIONHandle[0],
+                              __FILE__, __LINE__);
 #endif
 
-    for(i=0;i<(IMG_INT32)ui32PageCount;i++)
+    for(i = 0; i < 2; i++)
     {
-#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15))              
-#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0))               
-        ClearPageReserved(pvPageList[i]);
-#else
-        mem_map_reserve(pvPageList[i]);
-#endif         
-#endif 
-        __free_pages(pvPageList[i], 0);
+        if (!psLinuxMemArea->uData.sIONTilerAlloc.psIONHandle[i])
+            break;
+        ion_free(gpsIONClient, psLinuxMemArea->uData.sIONTilerAlloc.psIONHandle[i]);
+        psLinuxMemArea->uData.sIONTilerAlloc.psIONHandle[i] = IMG_NULL;
     }
 
-    (IMG_VOID) OSFreeMem(0, sizeof(*pvPageList) * ui32PageCount, pvPageList, hBlockPageList);
-       psLinuxMemArea->uData.sPageList.pvPageList = IMG_NULL; 
+    /* free copy of page list, originals are freed by ion_free */
+    vfree(psLinuxMemArea->uData.sIONTilerAlloc.pCPUPhysAddrs);
+    psLinuxMemArea->uData.sIONTilerAlloc.pCPUPhysAddrs = IMG_NULL;
 
     LinuxMemAreaStructFree(psLinuxMemArea);
 }
 
+#endif /* defined(CONFIG_ION_OMAP) */
 
 struct page*
 LinuxMemAreaOffsetToPage(LinuxMemArea *psLinuxMemArea,
@@ -1084,11 +1623,11 @@ LinuxMemAreaOffsetToPage(LinuxMemArea *psLinuxMemArea,
     IMG_UINT32 ui32PageIndex;
     IMG_CHAR *pui8Addr;
 
-    switch(psLinuxMemArea->eAreaType)
+    switch (psLinuxMemArea->eAreaType)
     {
         case LINUX_MEM_AREA_ALLOC_PAGES:
             ui32PageIndex = PHYS_TO_PFN(ui32ByteOffset);
-            return psLinuxMemArea->uData.sPageList.pvPageList[ui32PageIndex];
+            return psLinuxMemArea->uData.sPageList.ppsPageList[ui32PageIndex];
  
         case LINUX_MEM_AREA_VMALLOC:
             pui8Addr = psLinuxMemArea->uData.sVmalloc.pvVmallocAddress;
@@ -1096,7 +1635,7 @@ LinuxMemAreaOffsetToPage(LinuxMemArea *psLinuxMemArea,
             return vmalloc_to_page(pui8Addr);
  
         case LINUX_MEM_AREA_SUB_ALLOC:
-             
+            /* PRQA S 3670 3 */ /* ignore recursive warning */
             return LinuxMemAreaOffsetToPage(psLinuxMemArea->uData.sSubAlloc.psParentLinuxMemArea,
                                             psLinuxMemArea->uData.sSubAlloc.ui32ByteOffset
                                              + ui32ByteOffset);
@@ -1121,8 +1660,8 @@ KMemCacheCreateWrapper(IMG_CHAR *pszName,
     return kmem_cache_create(pszName, Size, Align, ui32Flags, NULL
 #if (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22))
                                , NULL
-#endif 
-                           );
+#endif /* (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22) */
+                          );
 }
 
 
@@ -1156,7 +1695,7 @@ _KMemCacheAllocWrapper(LinuxKMemCache *psCache,
                            kmem_cache_size(psCache),
                            pszFileName,
                            ui32Line
-                           );
+                          );
 #else
     PVR_UNREFERENCED_PARAMETER(pszFileName);
     PVR_UNREFERENCED_PARAMETER(ui32Line);
@@ -1166,30 +1705,6 @@ _KMemCacheAllocWrapper(LinuxKMemCache *psCache,
 }
 
 
-IMG_VOID
-_KMemCacheFreeWrapper(LinuxKMemCache *psCache, IMG_VOID *pvObject, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line)
-{
-#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
-    DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE, pvObject, pszFileName, ui32Line);
-#else
-    PVR_UNREFERENCED_PARAMETER(pszFileName);
-    PVR_UNREFERENCED_PARAMETER(ui32Line);
-#endif
-
-    kmem_cache_free(psCache, pvObject);
-}
-
-
-const IMG_CHAR *
-KMemCacheNameWrapper(LinuxKMemCache *psCache)
-{
-    PVR_UNREFERENCED_PARAMETER(psCache);
-
-    
-    return "";
-}
-
-
 LinuxMemArea *
 NewSubLinuxMemArea(LinuxMemArea *psParentLinuxMemArea,
                    IMG_UINT32 ui32ByteOffset,
@@ -1200,7 +1715,7 @@ NewSubLinuxMemArea(LinuxMemArea *psParentLinuxMemArea,
     PVR_ASSERT((ui32ByteOffset+ui32Bytes) <= psParentLinuxMemArea->ui32ByteSize);
     
     psLinuxMemArea = LinuxMemAreaStructAlloc();
-    if(!psLinuxMemArea)
+    if (!psLinuxMemArea)
     {
         return NULL;
     }
@@ -1234,7 +1749,7 @@ FreeSubLinuxMemArea(LinuxMemArea *psLinuxMemArea)
     DebugLinuxMemAreaRecordRemove(psLinuxMemArea);
 #endif
     
-    
+    /* Nothing more to do than free the LinuxMemArea structure */
 
     LinuxMemAreaStructFree(psLinuxMemArea);
 }
@@ -1243,14 +1758,15 @@ FreeSubLinuxMemArea(LinuxMemArea *psLinuxMemArea)
 static LinuxMemArea *
 LinuxMemAreaStructAlloc(IMG_VOID)
 {
+/* debug */
 #if 0
     LinuxMemArea *psLinuxMemArea;
-    psLinuxMemArea = kmem_cache_alloc(psLinuxMemAreaCache, GFP_KERNEL);
+    psLinuxMemArea = kmem_cache_alloc(g_PsLinuxMemAreaCache, GFP_KERNEL);
     printk(KERN_ERR "%s: psLinuxMemArea=%p\n", __FUNCTION__, psLinuxMemArea);
     dump_stack();
     return psLinuxMemArea;
 #else
-    return KMemCacheAllocWrapper(psLinuxMemAreaCache, GFP_KERNEL);
+    return KMemCacheAllocWrapper(g_PsLinuxMemAreaCache, GFP_KERNEL);
 #endif
 }
 
@@ -1258,16 +1774,16 @@ LinuxMemAreaStructAlloc(IMG_VOID)
 static IMG_VOID
 LinuxMemAreaStructFree(LinuxMemArea *psLinuxMemArea)
 {
-    KMemCacheFreeWrapper(psLinuxMemAreaCache, psLinuxMemArea);
-    
-    
+    KMemCacheFreeWrapper(g_PsLinuxMemAreaCache, psLinuxMemArea);
+    /* debug */
+    //printk(KERN_ERR "%s(%p)\n", __FUNCTION__, psLinuxMemArea);
 }
 
 
 IMG_VOID
 LinuxMemAreaDeepFree(LinuxMemArea *psLinuxMemArea)
 {
-    switch(psLinuxMemArea->eAreaType)
+    switch (psLinuxMemArea->eAreaType)
     {
         case LINUX_MEM_AREA_VMALLOC:
             FreeVMallocLinuxMemArea(psLinuxMemArea);
@@ -1278,15 +1794,18 @@ LinuxMemAreaDeepFree(LinuxMemArea *psLinuxMemArea)
         case LINUX_MEM_AREA_IOREMAP:
             FreeIORemapLinuxMemArea(psLinuxMemArea);
             break;
-       case LINUX_MEM_AREA_EXTERNAL_KV:
-           FreeExternalKVLinuxMemArea(psLinuxMemArea);
-           break;
+        case LINUX_MEM_AREA_EXTERNAL_KV:
+            FreeExternalKVLinuxMemArea(psLinuxMemArea);
+            break;
         case LINUX_MEM_AREA_IO:
             FreeIOLinuxMemArea(psLinuxMemArea);
             break;
         case LINUX_MEM_AREA_SUB_ALLOC:
             FreeSubLinuxMemArea(psLinuxMemArea);
             break;
+        case LINUX_MEM_AREA_ION:
+            FreeIONLinuxMemArea(psLinuxMemArea);
+            break;
         default:
             PVR_DPF((PVR_DBG_ERROR, "%s: Unknown are type (%d)\n",
                      __FUNCTION__, psLinuxMemArea->eAreaType));
@@ -1304,21 +1823,21 @@ DebugLinuxMemAreaRecordAdd(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32Flags)
     
     LinuxLockMutex(&g_sDebugMutex);
 
-    if(psLinuxMemArea->eAreaType != LINUX_MEM_AREA_SUB_ALLOC)
+    if (psLinuxMemArea->eAreaType != LINUX_MEM_AREA_SUB_ALLOC)
     {
         g_LinuxMemAreaWaterMark += psLinuxMemArea->ui32ByteSize;
-        if(g_LinuxMemAreaWaterMark > g_LinuxMemAreaHighWaterMark)
+        if (g_LinuxMemAreaWaterMark > g_LinuxMemAreaHighWaterMark)
         {
             g_LinuxMemAreaHighWaterMark = g_LinuxMemAreaWaterMark;
         }
     }
     g_LinuxMemAreaCount++;
     
-    
+    /* Create a new memory allocation record */
     psNewRecord = kmalloc(sizeof(DEBUG_LINUX_MEM_AREA_REC), GFP_KERNEL);
-    if(psNewRecord)
+    if (psNewRecord)
     {
-        
+        /* Record the allocation */
         psNewRecord->psLinuxMemArea = psLinuxMemArea;
         psNewRecord->ui32Flags = ui32Flags;
         psNewRecord->pid = OSGetCurrentProcessIDKM();
@@ -1332,16 +1851,16 @@ DebugLinuxMemAreaRecordAdd(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32Flags)
                  __FUNCTION__));
     }
     
-    
+    /* Sanity check the flags */
     pi8FlagsString = HAPFlagsToString(ui32Flags);
-    if(strstr(pi8FlagsString, "UNKNOWN"))
+    if (strstr(pi8FlagsString, "UNKNOWN"))
     {
         PVR_DPF((PVR_DBG_ERROR,
                  "%s: Unexpected flags (0x%08x) associated with psLinuxMemArea @ %p",
                  __FUNCTION__,
                  ui32Flags,
                  psLinuxMemArea));
-        
+        //dump_stack();
     }
 
     LinuxUnLockMutex(&g_sDebugMutex);
@@ -1355,7 +1874,7 @@ static IMG_VOID* MatchLinuxMemArea_AnyVaCb(DEBUG_LINUX_MEM_AREA_REC *psCurrentRe
        LinuxMemArea *psLinuxMemArea;
        
        psLinuxMemArea = va_arg(va, LinuxMemArea*);
-       if(psCurrentRecord->psLinuxMemArea == psLinuxMemArea)
+       if (psCurrentRecord->psLinuxMemArea == psLinuxMemArea)
        {
                return psCurrentRecord;
        }
@@ -1376,6 +1895,7 @@ DebugLinuxMemAreaRecordFind(LinuxMemArea *psLinuxMemArea)
                                                                                                                MatchLinuxMemArea_AnyVaCb,
                                                                                                                psLinuxMemArea);
        
+/*exit_unlock:*/
     LinuxUnLockMutex(&g_sDebugMutex);
 
     return psCurrentRecord;
@@ -1389,19 +1909,19 @@ DebugLinuxMemAreaRecordRemove(LinuxMemArea *psLinuxMemArea)
 
     LinuxLockMutex(&g_sDebugMutex);
 
-    if(psLinuxMemArea->eAreaType != LINUX_MEM_AREA_SUB_ALLOC)
+    if (psLinuxMemArea->eAreaType != LINUX_MEM_AREA_SUB_ALLOC)
     {
         g_LinuxMemAreaWaterMark -= psLinuxMemArea->ui32ByteSize;
     }
     g_LinuxMemAreaCount--;
 
-    
+    /* Locate the corresponding allocation entry */
        psCurrentRecord = List_DEBUG_LINUX_MEM_AREA_REC_Any_va(g_LinuxMemAreaRecords,
                                                                                                                MatchLinuxMemArea_AnyVaCb,
                                                                                                                psLinuxMemArea);
-       if(psCurrentRecord)
+       if (psCurrentRecord)
        {
-               
+               /* Unlink the allocation record */
                List_DEBUG_LINUX_MEM_AREA_REC_Remove(psCurrentRecord);
                kfree(psCurrentRecord);
        }
@@ -1419,7 +1939,7 @@ DebugLinuxMemAreaRecordRemove(LinuxMemArea *psLinuxMemArea)
 IMG_VOID *
 LinuxMemAreaToCpuVAddr(LinuxMemArea *psLinuxMemArea)
 {
-    switch(psLinuxMemArea->eAreaType)
+    switch (psLinuxMemArea->eAreaType)
     {
         case LINUX_MEM_AREA_VMALLOC:
             return psLinuxMemArea->uData.sVmalloc.pvVmallocAddress;
@@ -1430,8 +1950,8 @@ LinuxMemAreaToCpuVAddr(LinuxMemArea *psLinuxMemArea)
         case LINUX_MEM_AREA_SUB_ALLOC:
         {
             IMG_CHAR *pAddr =
-                LinuxMemAreaToCpuVAddr(psLinuxMemArea->uData.sSubAlloc.psParentLinuxMemArea);  
-            if(!pAddr)
+                LinuxMemAreaToCpuVAddr(psLinuxMemArea->uData.sSubAlloc.psParentLinuxMemArea); /* PRQA S 3670 */ /* ignore recursive warning */
+            if (!pAddr)
             {
                 return NULL;
             }
@@ -1450,7 +1970,7 @@ LinuxMemAreaToCpuPAddr(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32ByteOffset)
     
     CpuPAddr.uiAddr = 0;
 
-    switch(psLinuxMemArea->eAreaType)
+    switch (psLinuxMemArea->eAreaType)
     {
         case LINUX_MEM_AREA_IOREMAP:
         {
@@ -1490,11 +2010,18 @@ LinuxMemAreaToCpuPAddr(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32ByteOffset)
             CpuPAddr.uiAddr = VMallocToPhys(pCpuVAddr);
             break;
         }
+        case LINUX_MEM_AREA_ION:
+        {
+            IMG_UINT32 ui32PageIndex = PHYS_TO_PFN(ui32ByteOffset);
+            CpuPAddr = psLinuxMemArea->uData.sIONTilerAlloc.pCPUPhysAddrs[ui32PageIndex];
+            CpuPAddr.uiAddr += ADDR_TO_PAGE_OFFSET(ui32ByteOffset);
+            break;
+        }
         case LINUX_MEM_AREA_ALLOC_PAGES:
         {
             struct page *page;
             IMG_UINT32 ui32PageIndex = PHYS_TO_PFN(ui32ByteOffset);
-            page = psLinuxMemArea->uData.sPageList.pvPageList[ui32PageIndex];
+            page = psLinuxMemArea->uData.sPageList.ppsPageList[ui32PageIndex];
             CpuPAddr.uiAddr = page_to_phys(page);
             CpuPAddr.uiAddr += ADDR_TO_PAGE_OFFSET(ui32ByteOffset);
             break;
@@ -1523,22 +2050,23 @@ LinuxMemAreaToCpuPAddr(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32ByteOffset)
 IMG_BOOL
 LinuxMemAreaPhysIsContig(LinuxMemArea *psLinuxMemArea)
 {
-    switch(psLinuxMemArea->eAreaType)
+    switch (psLinuxMemArea->eAreaType)
     {
         case LINUX_MEM_AREA_IOREMAP:
         case LINUX_MEM_AREA_IO:
             return IMG_TRUE;
 
-       case LINUX_MEM_AREA_EXTERNAL_KV:
-           return psLinuxMemArea->uData.sExternalKV.bPhysContig;
+        case LINUX_MEM_AREA_EXTERNAL_KV:
+            return psLinuxMemArea->uData.sExternalKV.bPhysContig;
 
+        case LINUX_MEM_AREA_ION:
         case LINUX_MEM_AREA_VMALLOC:
         case LINUX_MEM_AREA_ALLOC_PAGES:
-           return IMG_FALSE;
+            return IMG_FALSE;
 
         case LINUX_MEM_AREA_SUB_ALLOC:
-             
-           return LinuxMemAreaPhysIsContig(psLinuxMemArea->uData.sSubAlloc.psParentLinuxMemArea);
+            /* PRQA S 3670 1 */ /* ignore recursive warning */
+            return LinuxMemAreaPhysIsContig(psLinuxMemArea->uData.sSubAlloc.psParentLinuxMemArea);
 
         default:
             PVR_DPF((PVR_DBG_ERROR, "%s: Unknown LinuxMemArea type (%d)\n",
@@ -1552,8 +2080,10 @@ LinuxMemAreaPhysIsContig(LinuxMemArea *psLinuxMemArea)
 const IMG_CHAR *
 LinuxMemAreaTypeToString(LINUX_MEM_AREA_TYPE eMemAreaType)
 {
-    
-    switch(eMemAreaType)
+    /* Note we explicitly check the types instead of e.g.
+     * using the type to index an array of strings so
+     * we remain orthogonal to enum changes */
+    switch (eMemAreaType)
     {
         case LINUX_MEM_AREA_IOREMAP:
             return "LINUX_MEM_AREA_IOREMAP";
@@ -1567,6 +2097,8 @@ LinuxMemAreaTypeToString(LINUX_MEM_AREA_TYPE eMemAreaType)
             return "LINUX_MEM_AREA_SUB_ALLOC";
         case LINUX_MEM_AREA_ALLOC_PAGES:
             return "LINUX_MEM_AREA_ALLOC_PAGES";
+        case LINUX_MEM_AREA_ION:
+            return "LINUX_MEM_AREA_ION";
         default:
             PVR_ASSERT(0);
     }
@@ -1578,7 +2110,7 @@ LinuxMemAreaTypeToString(LINUX_MEM_AREA_TYPE eMemAreaType)
 #if defined(DEBUG_LINUX_MEM_AREAS) || defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 static void ProcSeqStartstopDebugMutex(struct seq_file *sfile, IMG_BOOL start) 
 {
-       if(start) 
+       if (start) 
        {
            LinuxLockMutex(&g_sDebugMutex);             
        }
@@ -1587,7 +2119,7 @@ static void ProcSeqStartstopDebugMutex(struct seq_file *sfile, IMG_BOOL start)
            LinuxUnLockMutex(&g_sDebugMutex);
        }
 }
-#endif 
+#endif /* defined(DEBUG_LINUX_MEM_AREAS) || defined(DEBUG_LINUX_MEMORY_ALLOCATIONS) */
 
 #if defined(DEBUG_LINUX_MEM_AREAS)
 
@@ -1604,7 +2136,7 @@ static IMG_VOID* DecOffMemAreaRec_AnyVaCb(DEBUG_LINUX_MEM_AREA_REC *psNode, va_l
        }
 }
 
+/* seq_file version of generating output, for reference check proc.c:CreateProcReadEntrySeq */ 
 static void* ProcSeqNextMemArea(struct seq_file *sfile,void* el,loff_t off) 
 {
     DEBUG_LINUX_MEM_AREA_REC *psRecord;
@@ -1618,7 +2150,7 @@ static void* ProcSeqNextMemArea(struct seq_file *sfile,void* el,loff_t off)
 static void* ProcSeqOff2ElementMemArea(struct seq_file * sfile, loff_t off)
 {
     DEBUG_LINUX_MEM_AREA_REC *psRecord;
-       if(!off) 
+       if (!off) 
        {
                return PVR_PROC_SEQ_START_TOKEN;
        }
@@ -1634,11 +2166,11 @@ static void* ProcSeqOff2ElementMemArea(struct seq_file * sfile, loff_t off)
 static void ProcSeqShowMemArea(struct seq_file *sfile,void* el)
 {
     DEBUG_LINUX_MEM_AREA_REC *psRecord = (DEBUG_LINUX_MEM_AREA_REC*)el; 
-       if(el == PVR_PROC_SEQ_START_TOKEN) 
+       if (el == PVR_PROC_SEQ_START_TOKEN) 
        {
 
 #if !defined(DEBUG_LINUX_XML_PROC_FILES)
-        seq_printf( sfile,
+        seq_printf(sfile,
                                  "Number of Linux Memory Areas: %u\n"
                           "At the current water mark these areas correspond to %u bytes (excluding SUB areas)\n"
                           "At the highest water mark these areas corresponded to %u bytes (excluding SUB areas)\n"
@@ -1654,23 +2186,23 @@ static void ProcSeqShowMemArea(struct seq_file *sfile,void* el)
                           "Bytes",
                           "Pid",
                           "Flags"
-                         );
+                        );
 #else
-        seq_printf( sfile,
+        seq_printf(sfile,
                           "<mem_areas_header>\n"
                           "\t<count>%u</count>\n"
-                          "\t<watermark key=\"mar0\" description=\"current\" bytes=\"%u\"/>\n" 
-                          "\t<watermark key=\"mar1\" description=\"high\" bytes=\"%u\"/>\n" 
+                          "\t<watermark key=\"mar0\" description=\"current\" bytes=\"%u\"/>\n" /* (excluding SUB areas) */
+                          "\t<watermark key=\"mar1\" description=\"high\" bytes=\"%u\"/>\n" /* (excluding SUB areas) */
                           "</mem_areas_header>\n",
                           g_LinuxMemAreaCount,
                           g_LinuxMemAreaWaterMark,
                           g_LinuxMemAreaHighWaterMark
-                         );
+                        );
 #endif
                return;
        }
 
-        seq_printf( sfile,
+        seq_printf(sfile,
 #if !defined(DEBUG_LINUX_XML_PROC_FILES)
                        "%8p       %-24s %8p %08x %-8d %-5u %08x=(%s)\n",
 #else
@@ -1679,9 +2211,9 @@ static void ProcSeqShowMemArea(struct seq_file *sfile,void* el)
                        "\t<type>%s</type>\n"
                        "\t<cpu_virtual>%8p</cpu_virtual>\n"
                        "\t<cpu_physical>%08x</cpu_physical>\n"
-                       "\t<bytes>%ld</bytes>\n"
+                       "\t<bytes>%d</bytes>\n"
                        "\t<pid>%u</pid>\n"
-                       "\t<flags>%08lx</flags>\n"
+                       "\t<flags>%08x</flags>\n"
                        "\t<flags_string>%s</flags_string>\n"
                        "</linux_mem_area>\n",
 #endif
@@ -1693,11 +2225,11 @@ static void ProcSeqShowMemArea(struct seq_file *sfile,void* el)
                        psRecord->pid,
                        psRecord->ui32Flags,
                        HAPFlagsToString(psRecord->ui32Flags)
-                      );
+                     );
 
 }
 
-#endif 
+#endif /* DEBUG_LINUX_MEM_AREAS */
 
 
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
@@ -1716,7 +2248,7 @@ static IMG_VOID* DecOffMemAllocRec_AnyVaCb(DEBUG_MEM_ALLOC_REC *psNode, va_list
 }
 
 
+/* seq_file version of generating output, for reference check proc.c:CreateProcReadEntrySeq */ 
 static void* ProcSeqNextMemoryRecords(struct seq_file *sfile,void* el,loff_t off) 
 {
     DEBUG_MEM_ALLOC_REC *psRecord;
@@ -1725,9 +2257,9 @@ static void* ProcSeqNextMemoryRecords(struct seq_file *sfile,void* el,loff_t off
                                                                                DecOffMemAllocRec_AnyVaCb,
                                                                                &off);
 #if defined(DEBUG_LINUX_XML_PROC_FILES)
-       if(!psRecord) 
+       if (!psRecord) 
        {
-               seq_printf( sfile, "</meminfo>\n");
+               seq_printf(sfile, "</meminfo>\n");
        }
 #endif
 
@@ -1737,7 +2269,7 @@ static void* ProcSeqNextMemoryRecords(struct seq_file *sfile,void* el,loff_t off
 static void* ProcSeqOff2ElementMemoryRecords(struct seq_file *sfile, loff_t off)
 {
     DEBUG_MEM_ALLOC_REC *psRecord;
-       if(!off) 
+       if (!off) 
        {
                return PVR_PROC_SEQ_START_TOKEN;
        }
@@ -1748,9 +2280,9 @@ static void* ProcSeqOff2ElementMemoryRecords(struct seq_file *sfile, loff_t off)
                                                                                &off);
 
 #if defined(DEBUG_LINUX_XML_PROC_FILES)
-       if(!psRecord) 
+       if (!psRecord) 
        {
-               seq_printf( sfile, "</meminfo>\n");
+               seq_printf(sfile, "</meminfo>\n");
        }
 #endif
 
@@ -1760,64 +2292,78 @@ static void* ProcSeqOff2ElementMemoryRecords(struct seq_file *sfile, loff_t off)
 static void ProcSeqShowMemoryRecords(struct seq_file *sfile,void* el)
 {
     DEBUG_MEM_ALLOC_REC *psRecord = (DEBUG_MEM_ALLOC_REC*)el;
-       if(el == PVR_PROC_SEQ_START_TOKEN) 
+       if (el == PVR_PROC_SEQ_START_TOKEN) 
        {
 #if !defined(DEBUG_LINUX_XML_PROC_FILES)
-        
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        /* NOTE: If you update this code, please also update the XML varient below
+         * too! */
+
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Current Water Mark of bytes allocated via kmalloc",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_KMALLOC]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Highest Water Mark of bytes allocated via kmalloc",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_KMALLOC]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Current Water Mark of bytes allocated via vmalloc",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_VMALLOC]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Highest Water Mark of bytes allocated via vmalloc",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_VMALLOC]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Current Water Mark of bytes allocated via alloc_pages",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Highest Water Mark of bytes allocated via alloc_pages",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Current Water Mark of bytes allocated via ioremap",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_IOREMAP]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Highest Water Mark of bytes allocated via ioremap",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_IOREMAP]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Current Water Mark of bytes reserved for \"IO\" memory areas",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_IO]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Highest Water Mark of bytes allocated for \"IO\" memory areas",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_IO]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Current Water Mark of bytes allocated via kmem_cache_alloc",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE]);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "Highest Water Mark of bytes allocated via kmem_cache_alloc",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE]);
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+        seq_printf(sfile, "%-60s: %d bytes\n",
+                           "Current Water Mark of bytes mapped via vmap",
+                           g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_VMAP]);
+        seq_printf(sfile, "%-60s: %d bytes\n",
+                           "Highest Water Mark of bytes mapped via vmap",
+                           g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_VMAP]);
+#endif
+#if (PVR_LINUX_MEM_AREA_POOL_MAX_PAGES != 0)
+        seq_printf(sfile, "%-60s: %d pages\n",
+                           "Number of pages in page pool",
+                           atomic_read(&g_sPagePoolEntryCount));
+#endif
         seq_printf( sfile, "\n");
-
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "The Current Water Mark for memory allocated from system RAM",
-                           g_SysRAMWaterMark);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+                           SysRAMTrueWaterMark());
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "The Highest Water Mark for memory allocated from system RAM",
                            g_SysRAMHighWaterMark);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "The Current Water Mark for memory allocated from IO memory",
                            g_IOMemWaterMark);
-        seq_printf( sfile, "%-60s: %d bytes\n",
+        seq_printf(sfile, "%-60s: %d bytes\n",
                            "The Highest Water Mark for memory allocated from IO memory",
                            g_IOMemHighWaterMark);
 
         seq_printf( sfile, "\n");
 
-               seq_printf( sfile, "Details for all known allocations:\n"
+               seq_printf(sfile, "Details for all known allocations:\n"
                            "%-16s %-8s %-8s %-10s %-5s %-10s %s\n",
                            "Type",
                            "CpuVAddr",
@@ -1827,70 +2373,84 @@ static void ProcSeqShowMemoryRecords(struct seq_file *sfile,void* el)
                            "PrivateData",
                            "Filename:Line");
 
-#else 
-               
+#else /* DEBUG_LINUX_XML_PROC_FILES */
                
-               seq_printf( sfile, "<meminfo>\n<meminfo_header>\n");
-               seq_printf( sfile,
+               /* Note: If you want to update the description property of a watermark
+                * ensure that the key property remains unchanged so that watermark data
+                * logged over time from different driver revisions may remain comparable
+                */
+               seq_printf(sfile, "<meminfo>\n<meminfo_header>\n");
+               seq_printf(sfile,
                            "<watermark key=\"mr0\" description=\"kmalloc_current\" bytes=\"%d\"/>\n",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_KMALLOC]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr1\" description=\"kmalloc_high\" bytes=\"%d\"/>\n",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_KMALLOC]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr2\" description=\"vmalloc_current\" bytes=\"%d\"/>\n",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_VMALLOC]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr3\" description=\"vmalloc_high\" bytes=\"%d\"/>\n",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_VMALLOC]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr4\" description=\"alloc_pages_current\" bytes=\"%d\"/>\n",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr5\" description=\"alloc_pages_high\" bytes=\"%d\"/>\n",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr6\" description=\"ioremap_current\" bytes=\"%d\"/>\n",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_IOREMAP]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr7\" description=\"ioremap_high\" bytes=\"%d\"/>\n",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_IOREMAP]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr8\" description=\"io_current\" bytes=\"%d\"/>\n",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_IO]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr9\" description=\"io_high\" bytes=\"%d\"/>\n",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_IO]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr10\" description=\"kmem_cache_current\" bytes=\"%d\"/>\n",
                            g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE]);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr11\" description=\"kmem_cache_high\" bytes=\"%d\"/>\n",
                            g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE]);
-               seq_printf( sfile,"\n" );
-
-               seq_printf( sfile,
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+               seq_printf(sfile,
+                           "<watermark key=\"mr12\" description=\"vmap_current\" bytes=\"%d\"/>\n",
+                           g_WaterMarkData[DEBUG_MEM_ALLOC_TYPE_VMAP]);
+               seq_printf(sfile,
+                           "<watermark key=\"mr13\" description=\"vmap_high\" bytes=\"%d\"/>\n",
+                           g_HighWaterMarkData[DEBUG_MEM_ALLOC_TYPE_VMAP]);
+#endif
+               seq_printf(sfile,
                            "<watermark key=\"mr14\" description=\"system_ram_current\" bytes=\"%d\"/>\n",
-                           g_SysRAMWaterMark);
-               seq_printf( sfile,
+                           SysRAMTrueWaterMark());
+               seq_printf(sfile,
                            "<watermark key=\"mr15\" description=\"system_ram_high\" bytes=\"%d\"/>\n",
                            g_SysRAMHighWaterMark);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr16\" description=\"system_io_current\" bytes=\"%d\"/>\n",
                            g_IOMemWaterMark);
-               seq_printf( sfile,
+               seq_printf(sfile,
                            "<watermark key=\"mr17\" description=\"system_io_high\" bytes=\"%d\"/>\n",
                            g_IOMemHighWaterMark);
 
-               seq_printf( sfile, "</meminfo_header>\n");
+#if (PVR_LINUX_MEM_AREA_POOL_MAX_PAGES != 0)
+               seq_printf(sfile,
+                           "<watermark key=\"mr18\" description=\"page_pool_current\" bytes=\"%d\"/>\n",
+                           PAGES_TO_BYTES(atomic_read(&g_sPagePoolEntryCount)));
+#endif
+               seq_printf(sfile, "</meminfo_header>\n");
 
-#endif 
+#endif /* DEBUG_LINUX_XML_PROC_FILES */
                return;
        }
 
-    if(psRecord->eAllocType != DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE)
+    if (psRecord->eAllocType != DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE)
     {
-               seq_printf( sfile,
+               seq_printf(sfile,
 #if !defined(DEBUG_LINUX_XML_PROC_FILES)
                            "%-16s %-8p %08x %-10d %-5d %-10s %s:%d\n",
 #else
@@ -1916,7 +2476,7 @@ static void ProcSeqShowMemoryRecords(struct seq_file *sfile,void* el)
     }
     else
     {
-               seq_printf( sfile,
+               seq_printf(sfile,
 #if !defined(DEBUG_LINUX_XML_PROC_FILES)
                            "%-16s %-8p %08x %-10d %-5d %-10s %s:%d\n",
 #else
@@ -1942,10 +2502,11 @@ static void ProcSeqShowMemoryRecords(struct seq_file *sfile,void* el)
     }
 }
 
-#endif 
+#endif /*  defined(DEBUG_LINUX_MEMORY_ALLOCATIONS) */
 
 
 #if defined(DEBUG_LINUX_MEM_AREAS) || defined(DEBUG_LINUX_MMAP_AREAS)
+/* This could be moved somewhere more general */
 const IMG_CHAR *
 HAPFlagsToString(IMG_UINT32 ui32Flags)
 {
@@ -1967,31 +2528,35 @@ HAPFlagsToString(IMG_UINT32 ui32Flags)
         "UNKNOWN"
     };
     
-    
-    if(ui32Flags & PVRSRV_HAP_UNCACHED){
-        ui32CacheTypeIndex=0;
-    }else if(ui32Flags & PVRSRV_HAP_CACHED){
-        ui32CacheTypeIndex=1;
-    }else if(ui32Flags & PVRSRV_HAP_WRITECOMBINE){
-        ui32CacheTypeIndex=2;
-    }else{
-        ui32CacheTypeIndex=3;
+    /* FIXME create an enum for the cache type that we can
+     * cast and select so we get compiler warnings when
+     * when this code isn't complete due to new flags */
+    if (ui32Flags & PVRSRV_HAP_UNCACHED) {
+        ui32CacheTypeIndex = 0;
+    } else if (ui32Flags & PVRSRV_HAP_CACHED) {
+        ui32CacheTypeIndex = 1;
+    } else if (ui32Flags & PVRSRV_HAP_WRITECOMBINE) {
+        ui32CacheTypeIndex = 2;
+    } else {
+        ui32CacheTypeIndex = 3;
         PVR_DPF((PVR_DBG_ERROR, "%s: unknown cache type (%u)",
                  __FUNCTION__, (ui32Flags & PVRSRV_HAP_CACHETYPE_MASK)));
     }
 
-    
-    if(ui32Flags & PVRSRV_HAP_KERNEL_ONLY){
+    /* FIXME create an enum for the map type that we can
+     * cast and select so we get compiler warnings when
+     * when this code isn't complete due to new flags */
+    if (ui32Flags & PVRSRV_HAP_KERNEL_ONLY) {
         ui32MapTypeIndex = 0;
-    }else if(ui32Flags & PVRSRV_HAP_SINGLE_PROCESS){
+    } else if (ui32Flags & PVRSRV_HAP_SINGLE_PROCESS) {
         ui32MapTypeIndex = 1;
-    }else if(ui32Flags & PVRSRV_HAP_MULTI_PROCESS){
+    } else if (ui32Flags & PVRSRV_HAP_MULTI_PROCESS) {
         ui32MapTypeIndex = 2;
-    }else if(ui32Flags & PVRSRV_HAP_FROM_EXISTING_PROCESS){
+    } else if (ui32Flags & PVRSRV_HAP_FROM_EXISTING_PROCESS) {
         ui32MapTypeIndex = 3;
-    }else if(ui32Flags & PVRSRV_HAP_NO_CPU_VIRTUAL){
+    } else if (ui32Flags & PVRSRV_HAP_NO_CPU_VIRTUAL) {
         ui32MapTypeIndex = 4;
-    }else{
+    } else {
         ui32MapTypeIndex = 5;
         PVR_DPF((PVR_DBG_ERROR, "%s: unknown map type (%u)",
                  __FUNCTION__, (ui32Flags & PVRSRV_HAP_MAPTYPE_MASK)));
@@ -2013,3 +2578,222 @@ HAPFlagsToString(IMG_UINT32 ui32Flags)
 }
 #endif
 
+#if defined(DEBUG_LINUX_MEM_AREAS)
+static IMG_VOID LinuxMMCleanup_MemAreas_ForEachCb(DEBUG_LINUX_MEM_AREA_REC *psCurrentRecord)
+{
+       LinuxMemArea *psLinuxMemArea;
+
+       psLinuxMemArea = psCurrentRecord->psLinuxMemArea;
+       PVR_DPF((PVR_DBG_ERROR, "%s: BUG!: Cleaning up Linux memory area (%p), type=%s, size=%d bytes",
+                               __FUNCTION__,
+                               psCurrentRecord->psLinuxMemArea,
+                               LinuxMemAreaTypeToString(psCurrentRecord->psLinuxMemArea->eAreaType),
+                               psCurrentRecord->psLinuxMemArea->ui32ByteSize));
+       /* Note this will also remove psCurrentRecord from g_LinuxMemAreaRecords
+        * but that's ok since we have already got a pointer to the next area. */
+       LinuxMemAreaDeepFree(psLinuxMemArea);
+}
+#endif
+
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+static IMG_VOID LinuxMMCleanup_MemRecords_ForEachVa(DEBUG_MEM_ALLOC_REC *psCurrentRecord)
+
+{
+       
+/* It's a bug if anything remains allocated at this point. We
+ * report an error, and simply brute force free anything we find. */
+       PVR_DPF((PVR_DBG_ERROR, "%s: BUG!: Cleaning up memory: "
+                                                       "type=%s "
+                                                       "CpuVAddr=%p "
+                                                       "CpuPAddr=0x%08x, "
+                                                       "allocated @ file=%s,line=%d",
+                       __FUNCTION__,
+                       DebugMemAllocRecordTypeToString(psCurrentRecord->eAllocType),
+                       psCurrentRecord->pvCpuVAddr,
+                       psCurrentRecord->ulCpuPAddr,
+                       psCurrentRecord->pszFileName,
+                       psCurrentRecord->ui32Line));
+       switch (psCurrentRecord->eAllocType)
+       {
+               case DEBUG_MEM_ALLOC_TYPE_KMALLOC:
+                       KFreeWrapper(psCurrentRecord->pvCpuVAddr);
+                       break;
+               case DEBUG_MEM_ALLOC_TYPE_IOREMAP:
+                       IOUnmapWrapper(psCurrentRecord->pvCpuVAddr);
+                       break;
+               case DEBUG_MEM_ALLOC_TYPE_IO:
+                       /* Nothing needed except to free the record */
+                       DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_IO, psCurrentRecord->pvKey, __FILE__, __LINE__);
+                       break;
+               case DEBUG_MEM_ALLOC_TYPE_VMALLOC:
+                       VFreeWrapper(psCurrentRecord->pvCpuVAddr);
+                       break;
+               case DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES:
+                       DebugMemAllocRecordRemove(DEBUG_MEM_ALLOC_TYPE_ALLOC_PAGES, psCurrentRecord->pvKey, __FILE__, __LINE__);
+                       break;
+               case DEBUG_MEM_ALLOC_TYPE_KMEM_CACHE:
+                       KMemCacheFreeWrapper(psCurrentRecord->pvPrivateData, psCurrentRecord->pvCpuVAddr);
+                       break;
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+               case DEBUG_MEM_ALLOC_TYPE_VMAP:
+                       VUnmapWrapper(psCurrentRecord->pvCpuVAddr);
+                       break;
+#endif
+               default:
+                       PVR_ASSERT(0);
+       }
+}
+#endif
+
+
+#if defined(PVR_LINUX_MEM_AREA_POOL_ALLOW_SHRINK)
+static struct shrinker g_sShrinker =
+{
+       .shrink = ShrinkPagePool,
+       .seeks = DEFAULT_SEEKS
+};
+
+static IMG_BOOL g_bShrinkerRegistered;
+#endif
+
+IMG_VOID
+LinuxMMCleanup(IMG_VOID)
+{
+#if defined(DEBUG_LINUX_MEM_AREAS)
+    {
+        if (g_LinuxMemAreaCount)
+        {
+            PVR_DPF((PVR_DBG_ERROR, "%s: BUG!: There are %d LinuxMemArea allocation unfreed (%d bytes)",
+                    __FUNCTION__, g_LinuxMemAreaCount, g_LinuxMemAreaWaterMark));
+        }
+               
+       List_DEBUG_LINUX_MEM_AREA_REC_ForEach(g_LinuxMemAreaRecords, LinuxMMCleanup_MemAreas_ForEachCb);
+
+       if (g_SeqFileMemArea)
+       {
+           RemoveProcEntrySeq(g_SeqFileMemArea);
+       }
+    }
+#endif
+
+#if defined(PVR_LINUX_MEM_AREA_POOL_ALLOW_SHRINK)
+       if (g_bShrinkerRegistered)
+       {
+               unregister_shrinker(&g_sShrinker);
+       }
+#endif
+
+    /*
+     * The page pool must be freed after any remaining mem areas, but before
+     * the remaining memory resources.
+     */
+    FreePagePool();
+
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+    {
+        
+        /*
+        * It's a bug if anything remains allocated at this point. We
+         * report an error, and simply brute force free anything we find.
+        */
+               List_DEBUG_MEM_ALLOC_REC_ForEach(g_MemoryRecords, LinuxMMCleanup_MemRecords_ForEachVa);
+
+               if (g_SeqFileMemoryRecords)
+               {
+                       RemoveProcEntrySeq(g_SeqFileMemoryRecords);
+               }
+    }
+#endif
+
+    if (g_PsLinuxMemAreaCache)
+    {
+        KMemCacheDestroyWrapper(g_PsLinuxMemAreaCache); 
+    }
+
+    if (g_PsLinuxPagePoolCache)
+    {
+        KMemCacheDestroyWrapper(g_PsLinuxPagePoolCache); 
+    }
+}
+
+PVRSRV_ERROR
+LinuxMMInit(IMG_VOID)
+{
+#if defined(DEBUG_LINUX_MEM_AREAS) || defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+       LinuxInitMutex(&g_sDebugMutex);
+#endif
+
+#if defined(DEBUG_LINUX_MEM_AREAS)
+    {
+               g_SeqFileMemArea = CreateProcReadEntrySeq(
+                                                                       "mem_areas", 
+                                                                       NULL, 
+                                                                       ProcSeqNextMemArea,
+                                                                       ProcSeqShowMemArea,
+                                                                       ProcSeqOff2ElementMemArea,
+                                                                       ProcSeqStartstopDebugMutex
+                                                                 );
+               if (!g_SeqFileMemArea)
+               {
+                   goto failed;
+               }
+    }
+#endif
+
+
+#if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
+    {
+               g_SeqFileMemoryRecords = CreateProcReadEntrySeq(
+                                                                       "meminfo", 
+                                                                       NULL, 
+                                                                       ProcSeqNextMemoryRecords,
+                                                                       ProcSeqShowMemoryRecords, 
+                                                                       ProcSeqOff2ElementMemoryRecords,
+                                                                       ProcSeqStartstopDebugMutex
+                                                                 );
+               if (!g_SeqFileMemoryRecords)
+               {
+                   goto failed;
+               }
+    }
+#endif
+
+    g_PsLinuxMemAreaCache = KMemCacheCreateWrapper("img-mm", sizeof(LinuxMemArea), 0, 0);
+    if (!g_PsLinuxMemAreaCache)
+    {
+        PVR_DPF((PVR_DBG_ERROR,"%s: failed to allocate mem area kmem_cache", __FUNCTION__));
+        goto failed;
+    }
+
+#if (PVR_LINUX_MEM_AREA_POOL_MAX_PAGES != 0)
+    g_iPagePoolMaxEntries = PVR_LINUX_MEM_AREA_POOL_MAX_PAGES;
+    if (g_iPagePoolMaxEntries <= 0 || g_iPagePoolMaxEntries > INT_MAX/2)
+    {
+       g_iPagePoolMaxEntries = INT_MAX/2;
+       PVR_TRACE(("%s: No limit set for page pool size", __FUNCTION__));
+    }
+    else
+    {
+       PVR_TRACE(("%s: Maximum page pool size: %d", __FUNCTION__, g_iPagePoolMaxEntries));
+    }
+
+    g_PsLinuxPagePoolCache = KMemCacheCreateWrapper("img-mm-pool", sizeof(LinuxPagePoolEntry), 0, 0);
+    if (!g_PsLinuxPagePoolCache)
+    {
+        PVR_DPF((PVR_DBG_ERROR,"%s: failed to allocate page pool kmem_cache", __FUNCTION__));
+        goto failed;
+    }
+#endif
+
+#if defined(PVR_LINUX_MEM_AREA_POOL_ALLOW_SHRINK)
+       register_shrinker(&g_sShrinker);
+       g_bShrinkerRegistered = IMG_TRUE;
+#endif
+
+    return PVRSRV_OK;
+
+failed:
+    LinuxMMCleanup();
+    return PVRSRV_ERROR_OUT_OF_MEMORY;
+}
+
index b32f5e8..d414306 100644 (file)
@@ -1,29 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Linux Memory Management.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Declares various memory management utility functions
+                for Linux.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __IMG_LINUX_MM_H__
 #define __IMG_LINUX_MM_H__
 
@@ -48,6 +64,8 @@
 
 #define        ADDR_TO_PAGE_OFFSET(addr) (((unsigned long)(addr)) & (PAGE_SIZE - 1))
 
+#define        PAGES_TO_BYTES(pages) ((pages) << PAGE_SHIFT)
+
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,10))
 #define        REMAP_PFN_RANGE(vma, addr, pfn, size, prot) remap_pfn_range(vma, addr, pfn, size, prot)
 #else
@@ -78,33 +96,43 @@ static inline IMG_UINT32 VMallocToPhys(IMG_VOID *pCpuVAddr)
 
 typedef enum {
     LINUX_MEM_AREA_IOREMAP,
-       LINUX_MEM_AREA_EXTERNAL_KV,
+    LINUX_MEM_AREA_EXTERNAL_KV,
     LINUX_MEM_AREA_IO,
     LINUX_MEM_AREA_VMALLOC,
     LINUX_MEM_AREA_ALLOC_PAGES,
     LINUX_MEM_AREA_SUB_ALLOC,
+    LINUX_MEM_AREA_ION,
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+    LINUX_MEM_AREA_VMAP,
+#endif
     LINUX_MEM_AREA_TYPE_COUNT
 }LINUX_MEM_AREA_TYPE;
 
 typedef struct _LinuxMemArea LinuxMemArea;
 
 
+/* FIXME - describe this structure. */
 struct _LinuxMemArea {
     LINUX_MEM_AREA_TYPE eAreaType;
     union _uData
     {
         struct _sIORemap
         {
-            
+            /* Note: The memory this represents is _not_ implicitly
+             * page aligned, neither is its size */
             IMG_CPU_PHYADDR CPUPhysAddr;
             IMG_VOID *pvIORemapCookie;
         }sIORemap;
         struct _sExternalKV
         {
-            
+            /* Note: The memory this represents is _not_ implicitly
+             * page aligned, neither is its size */
            IMG_BOOL bPhysContig;
            union {
-                   
+                   /*
+                    * SYSPhysAddr is valid if bPhysContig is true, else
+                    * pSysPhysAddr is valid
+                    */
                    IMG_SYS_PHYADDR SysPhysAddr;
                    IMG_SYS_PHYADDR *pSysPhysAddr;
            } uPhysAddr;
@@ -112,40 +140,60 @@ struct _LinuxMemArea {
         }sExternalKV;
         struct _sIO
         {
-            
+            /* Note: The memory this represents is _not_ implicitly
+             * page aligned, neither is its size */
             IMG_CPU_PHYADDR CPUPhysAddr;
         }sIO;
         struct _sVmalloc
         {
-            
+            /* Note the memory this represents _is_ implicitly
+             * page aligned _and_ so is its size */
             IMG_VOID *pvVmallocAddress;
+#if defined(PVR_LINUX_MEM_AREA_USE_VMAP)
+            struct page **ppsPageList;
+           IMG_HANDLE hBlockPageList;
+#endif
         }sVmalloc;
         struct _sPageList
         {
-            
-            struct page **pvPageList;
+            /* Note the memory this represents _is_ implicitly
+             * page aligned _and_ so is its size */
+            struct page **ppsPageList;
            IMG_HANDLE hBlockPageList;
         }sPageList;
+        struct _sIONTilerAlloc
+        {
+            /* Note the memory this represents _is_ implicitly
+             * page aligned _and_ so is its size */
+            IMG_CPU_PHYADDR *pCPUPhysAddrs;
+            struct ion_handle *psIONHandle[2];
+        }sIONTilerAlloc;
         struct _sSubAlloc
         {
-            
+            /* Note: The memory this represents is _not_ implicitly
+             * page aligned, neither is its size */
             LinuxMemArea *psParentLinuxMemArea;
             IMG_UINT32 ui32ByteOffset;
         }sSubAlloc;
     }uData;
 
-    IMG_UINT32 ui32ByteSize;           
+    IMG_UINT32 ui32ByteSize;           /* Size of memory area */
+
+    IMG_UINT32 ui32AreaFlags;          /* Flags passed at creation time */
 
-    IMG_UINT32 ui32AreaFlags;          
+    IMG_BOOL bMMapRegistered;          /* Registered with mmap code */
 
-    IMG_BOOL bMMapRegistered;          
+    IMG_BOOL bNeedsCacheInvalidate;    /* Cache should be invalidated on first map? */
 
-    IMG_BOOL bNeedsCacheInvalidate;    
+       IMG_HANDLE hBMHandle;                   /* Handle back to BM for this allocation */
 
-    
+    /* List entry for global list of areas registered for mmap */
     struct list_head   sMMapItem;
 
-    
+    /*
+     * Head of list of all mmap offset structures associated with this
+     * memory area.
+     */
     struct list_head   sMMapOffsetStructList;
 };
 
@@ -156,12 +204,45 @@ typedef struct kmem_cache LinuxKMemCache;
 #endif
 
 
+/*!
+ *******************************************************************************
+ * @Function   LinuxMMInit
+ *
+ * @Description
+ *
+ * Initialise linux memory management code.
+ * This should be called during services initialisation.
+ *
+ * @Return none
+******************************************************************************/
 PVRSRV_ERROR LinuxMMInit(IMG_VOID);
 
 
+/*!
+ *******************************************************************************
+ *
+ * @Function   LinuxMMCleanup
+ *
+ * @Description
+ *
+ * Cleanup state for the linux memory management code.
+ * This should be called at services cleanup.
+ *
+ * @Return none
+******************************************************************************/
 IMG_VOID LinuxMMCleanup(IMG_VOID);
 
 
+/*!
+ *******************************************************************************
+ * @brief Wrappers for kmalloc/kfree with optional /proc/pvr/km tracking
+ *        They can also be used as more concise replacements for OSAllocMem
+ *        in Linux specific code.
+ *
+ * @param ui32ByteSize  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 #define KMallocWrapper(ui32ByteSize, uFlags) _KMallocWrapper(ui32ByteSize, uFlags, __FILE__, __LINE__)
 #else
@@ -170,6 +251,14 @@ IMG_VOID LinuxMMCleanup(IMG_VOID);
 IMG_VOID *_KMallocWrapper(IMG_UINT32 ui32ByteSize, gfp_t uFlags, IMG_CHAR *szFileName, IMG_UINT32 ui32Line);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param pvCpuVAddr  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 #define KFreeWrapper(pvCpuVAddr) _KFreeWrapper(pvCpuVAddr, __FILE__, __LINE__)
 #else
@@ -178,6 +267,15 @@ IMG_VOID *_KMallocWrapper(IMG_UINT32 ui32ByteSize, gfp_t uFlags, IMG_CHAR *szFil
 IMG_VOID _KFreeWrapper(IMG_VOID *pvCpuVAddr, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param ui32Bytes  
+ * @param ui32AllocFlags  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 #define VMallocWrapper(ui32Bytes, ui32AllocFlags) _VMallocWrapper(ui32Bytes, ui32AllocFlags, __FILE__, __LINE__)
 #else
@@ -186,6 +284,14 @@ IMG_VOID _KFreeWrapper(IMG_VOID *pvCpuVAddr, IMG_CHAR *pszFileName, IMG_UINT32 u
 IMG_VOID *_VMallocWrapper(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AllocFlags, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param pvCpuVAddr  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 #define VFreeWrapper(pvCpuVAddr) _VFreeWrapper(pvCpuVAddr, __FILE__, __LINE__)
 #else
@@ -194,12 +300,38 @@ IMG_VOID *_VMallocWrapper(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AllocFlags, IMG_C
 IMG_VOID _VFreeWrapper(IMG_VOID *pvCpuVAddr, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line);
 
 
+/*!
+ *******************************************************************************
+ * @brief Allocates virtually contiguous pages
+ *
+ * @param ui32Bytes  number of bytes to reserve
+ * @param ui32AreaFlags  Heap caching and mapping Flags
+ *
+ * @return Page-aligned address of virtual allocation or NULL on error
+ ******************************************************************************/
 LinuxMemArea *NewVMallocLinuxMemArea(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags);
 
 
+/*!
+ *******************************************************************************
+ * @brief Deallocates virtually contiguous pages
+ *
+ * @param LinuxMemArea from NewVMallocLinuxMemArea
+ *
+ ******************************************************************************/
 IMG_VOID FreeVMallocLinuxMemArea(LinuxMemArea *psLinuxMemArea);
 
 
+/*!
+ *******************************************************************************
+ * @brief Reserve physical IO memory and create a CPU virtual mapping for it
+ *
+ * @param BasePAddr 
+ * @param ui32Bytes  
+ * @param ui32MappingFlags  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 #define IORemapWrapper(BasePAddr, ui32Bytes, ui32MappingFlags) \
     _IORemapWrapper(BasePAddr, ui32Bytes, ui32MappingFlags, __FILE__, __LINE__)
@@ -214,17 +346,63 @@ IMG_VOID *_IORemapWrapper(IMG_CPU_PHYADDR BasePAddr,
                           IMG_UINT32 ui32Line);
 
 
+/*!
+ *******************************************************************************
+ * @brief Reserve physical IO memory and create a CPU virtual mapping for it
+ *
+ * @param BasePAddr  
+ * @param ui32Bytes  
+ * @param ui32AreaFlags  Heap caching and mapping Flags
+ *
+ * @return 
+ ******************************************************************************/
 LinuxMemArea *NewIORemapLinuxMemArea(IMG_CPU_PHYADDR BasePAddr, IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return 
+ ********************************************************************************/
 IMG_VOID FreeIORemapLinuxMemArea(LinuxMemArea *psLinuxMemArea);
 
+/*!
+ *******************************************************************************
+ * @brief Register physical memory which already has a CPU virtual mapping
+ *
+ * @param pBasePAddr  
+ * @param pvCPUVAddr  
+ * @param bPhysContig
+ * @param ui32Bytes  
+ * @param ui32AreaFlags  Heap caching and mapping Flags
+ *
+ * @return 
+ ******************************************************************************/
 LinuxMemArea *NewExternalKVLinuxMemArea(IMG_SYS_PHYADDR *pBasePAddr, IMG_VOID *pvCPUVAddr, IMG_UINT32 ui32Bytes, IMG_BOOL bPhysContig, IMG_UINT32 ui32AreaFlags);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return 
+ ******************************************************************************/
 IMG_VOID FreeExternalKVLinuxMemArea(LinuxMemArea *psLinuxMemArea);
 
 
+/*!
+ ******************************************************************************
+ * @brief Unmaps an IO memory mapping created using IORemap
+ *
+ * @param pvIORemapCookie  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 #define IOUnmapWrapper(pvIORemapCookie) \
     _IOUnmapWrapper(pvIORemapCookie, __FILE__, __LINE__)
@@ -235,15 +413,52 @@ IMG_VOID FreeExternalKVLinuxMemArea(LinuxMemArea *psLinuxMemArea);
 IMG_VOID _IOUnmapWrapper(IMG_VOID *pvIORemapCookie, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ * @param ui32ByteOffset  
+ *
+ * @return 
+ ******************************************************************************/
 struct page *LinuxMemAreaOffsetToPage(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32ByteOffset);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param pszName  
+ * @param Size  
+ * @param Align  
+ * @param ui32Flags  
+ *
+ * @return 
+ ******************************************************************************/
 LinuxKMemCache *KMemCacheCreateWrapper(IMG_CHAR *pszName, size_t Size, size_t Align, IMG_UINT32 ui32Flags);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psCache  
+ *
+ * @return 
+ ******************************************************************************/
 IMG_VOID KMemCacheDestroyWrapper(LinuxKMemCache *psCache);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psCache  
+ * @param Flags  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 #define KMemCacheAllocWrapper(psCache, Flags) _KMemCacheAllocWrapper(psCache, Flags, __FILE__, __LINE__)
 #else
@@ -256,6 +471,15 @@ IMG_VOID *_KMemCacheAllocWrapper(LinuxKMemCache *psCache, gfp_t Flags, IMG_CHAR
 IMG_VOID *_KMemCacheAllocWrapper(LinuxKMemCache *psCache, int Flags, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line);
 #endif
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psCache  
+ * @param pvObject  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 #define KMemCacheFreeWrapper(psCache, pvObject) _KMemCacheFreeWrapper(psCache, pvObject, __FILE__, __LINE__)
 #else
@@ -264,29 +488,146 @@ IMG_VOID *_KMemCacheAllocWrapper(LinuxKMemCache *psCache, int Flags, IMG_CHAR *p
 IMG_VOID _KMemCacheFreeWrapper(LinuxKMemCache *psCache, IMG_VOID *pvObject, IMG_CHAR *pszFileName, IMG_UINT32 ui32Line);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psCache  
+ *
+ * @return 
+ ******************************************************************************/
 const IMG_CHAR *KMemCacheNameWrapper(LinuxKMemCache *psCache);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param BasePAddr  
+ * @param ui32Bytes  
+ * @param ui32AreaFlags  Heap caching and mapping Flags
+ *
+ * @return 
+ ******************************************************************************/
 LinuxMemArea *NewIOLinuxMemArea(IMG_CPU_PHYADDR BasePAddr, IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return 
+ ******************************************************************************/
 IMG_VOID FreeIOLinuxMemArea(LinuxMemArea *psLinuxMemArea);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param ui32Bytes  
+ * @param ui32AreaFlags  E.g Heap caching and mapping Flags
+ *
+ * @return 
+ ******************************************************************************/
 LinuxMemArea *NewAllocPagesLinuxMemArea(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return 
+ ******************************************************************************/
 IMG_VOID FreeAllocPagesLinuxMemArea(LinuxMemArea *psLinuxMemArea);
 
 
+#if defined(CONFIG_ION_OMAP)
+
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param ui32Bytes  
+ * @param ui32AreaFlags  E.g Heap caching and mapping Flags
+ *
+ * @return 
+ ******************************************************************************/
+LinuxMemArea *
+NewIONLinuxMemArea(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags,
+                   IMG_PVOID pvPrivData, IMG_UINT32 ui32PrivDataLength);
+
+
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return 
+ ******************************************************************************/
+IMG_VOID FreeIONLinuxMemArea(LinuxMemArea *psLinuxMemArea);
+
+#else /* defined(CONFIG_ION_OMAP) */
+
+static inline LinuxMemArea *
+NewIONLinuxMemArea(IMG_UINT32 ui32Bytes, IMG_UINT32 ui32AreaFlags,
+                   IMG_PVOID pvPrivData, IMG_UINT32 ui32PrivDataLength)
+{
+    PVR_UNREFERENCED_PARAMETER(ui32Bytes);
+    PVR_UNREFERENCED_PARAMETER(ui32AreaFlags);
+    PVR_UNREFERENCED_PARAMETER(pvPrivData);
+    PVR_UNREFERENCED_PARAMETER(ui32PrivDataLength);
+    BUG();
+    return IMG_NULL;
+}
+
+static inline IMG_VOID FreeIONLinuxMemArea(LinuxMemArea *psLinuxMemArea)
+{
+    PVR_UNREFERENCED_PARAMETER(psLinuxMemArea);
+    BUG();
+}
+
+#endif /* defined(CONFIG_ION_OMAP) */
+
+
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psParentLinuxMemArea  
+ * @param ui32ByteOffset
+ * @param ui32Bytes
+ *
+ * @return 
+ ******************************************************************************/
 LinuxMemArea *NewSubLinuxMemArea(LinuxMemArea *psParentLinuxMemArea,
                                  IMG_UINT32 ui32ByteOffset,
                                  IMG_UINT32 ui32Bytes);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return 
+ ******************************************************************************/
 IMG_VOID LinuxMemAreaDeepFree(LinuxMemArea *psLinuxMemArea);
 
 
+/*!
+ *******************************************************************************
+ * @brief For debug builds, LinuxMemAreas are tracked in /proc
+ *
+ * @param psLinuxMemArea  
+ *
+ ******************************************************************************/
 #if defined(LINUX_MEM_AREAS_DEBUG)
 IMG_VOID LinuxMemAreaRegister(LinuxMemArea *psLinuxMemArea);
 #else
@@ -294,16 +635,49 @@ IMG_VOID LinuxMemAreaRegister(LinuxMemArea *psLinuxMemArea);
 #endif
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return 
+ ******************************************************************************/
 IMG_VOID *LinuxMemAreaToCpuVAddr(LinuxMemArea *psLinuxMemArea);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param psLinuxMemArea  
+ * @param ui32ByteOffset  
+ *
+ * @return 
+ ******************************************************************************/
 IMG_CPU_PHYADDR LinuxMemAreaToCpuPAddr(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32ByteOffset);
 
 
 #define         LinuxMemAreaToCpuPFN(psLinuxMemArea, ui32ByteOffset) PHYS_TO_PFN(LinuxMemAreaToCpuPAddr(psLinuxMemArea, ui32ByteOffset).uiAddr)
 
+/*!
+ *******************************************************************************
+ * @brief Indicate whether a LinuxMemArea is physically contiguous
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return IMG_TRUE if the physical address range is contiguous, else IMG_FALSE
+ ******************************************************************************/
 IMG_BOOL LinuxMemAreaPhysIsContig(LinuxMemArea *psLinuxMemArea);
 
+/*!
+ *******************************************************************************
+ * @brief Return the real underlying LinuxMemArea
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return The real underlying LinuxMemArea
+ ******************************************************************************/
 static inline LinuxMemArea *
 LinuxMemAreaRoot(LinuxMemArea *psLinuxMemArea)
 {
@@ -318,6 +692,14 @@ LinuxMemAreaRoot(LinuxMemArea *psLinuxMemArea)
 }
 
 
+/*!
+ *******************************************************************************
+ * @brief Return type of  real underlying LinuxMemArea
+ *
+ * @param psLinuxMemArea  
+ *
+ * @return The areas eAreaType or for SUB areas; return the parents eAreaType.
+ ******************************************************************************/
 static inline LINUX_MEM_AREA_TYPE
 LinuxMemAreaRootType(LinuxMemArea *psLinuxMemArea)
 {
@@ -325,12 +707,28 @@ LinuxMemAreaRootType(LinuxMemArea *psLinuxMemArea)
 }
 
 
+/*!
+ *******************************************************************************
+ * @brief Converts the enum type of a LinuxMemArea to a const string
+ *
+ * @param eMemAreaType  
+ *
+ * @return const string representation of type
+ ******************************************************************************/
 const IMG_CHAR *LinuxMemAreaTypeToString(LINUX_MEM_AREA_TYPE eMemAreaType);
 
 
+/*!
+ *******************************************************************************
+ * @brief 
+ *
+ * @param ui32Flags  
+ *
+ * @return 
+ ******************************************************************************/
 #if defined(DEBUG) || defined(DEBUG_LINUX_MEM_AREAS)
 const IMG_CHAR *HAPFlagsToString(IMG_UINT32 ui32Flags);
 #endif
 
-#endif 
+#endif /* __IMG_LINUX_MM_H__ */
 
index 00c8b9d..d088e06 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux mmap interface
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 
@@ -39,6 +54,9 @@
 #include <linux/wrapper.h>
 #endif
 #include <linux/slab.h>
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,26))
+#include <linux/highmem.h>
+#endif
 #include <asm/io.h>
 #include <asm/page.h>
 #include <asm/shmparam.h>
 #include <drm/drmP.h>
 #endif
 
-#include "img_defs.h"
-#include "services.h"
-#include "servicesint.h"
+#include "services_headers.h"
+
 #include "pvrmmap.h"
 #include "mutils.h"
 #include "mmap.h"
 #include "mm.h"
-#include "pvr_debug.h"
-#include "osfunc.h"
 #include "proc.h"
 #include "mutex.h"
 #include "handle.h"
 #error "The mmap code requires PVR_SECURE_HANDLES"
 #endif
 
-static PVRSRV_LINUX_MUTEX g_sMMapMutex;
+/* WARNING:
+ * The mmap code has its own mutex, to prevent a possible deadlock,
+ * when using gPVRSRVLock.
+ * The Linux kernel takes the mm->mmap_sem before calling the mmap
+ * entry points (PVRMMap, MMapVOpen, MMapVClose), but the ioctl
+ * entry point may take mm->mmap_sem during fault handling, or 
+ * before calling get_user_pages.  If gPVRSRVLock was used in the
+ * mmap entry points, a deadlock could result, due to the ioctl
+ * and mmap code taking the two locks in different orders.
+ * As a corollary to this, the mmap entry points must not call
+ * any driver code that relies on gPVRSRVLock is held.
+ */
+PVRSRV_LINUX_MUTEX g_sMMapMutex;
 
 static LinuxKMemCache *g_psMemmapCache = NULL;
 static LIST_HEAD(g_sMMapAreaList);
@@ -87,9 +114,28 @@ static IMG_UINT32 g_ui32TotalByteSize = 0;
 
 #if defined(DEBUG_LINUX_MMAP_AREAS)
 static struct proc_dir_entry *g_ProcMMap;
-#endif 
+#endif /* defined(DEBUG_LINUX_MMAP_AREAS) */
 
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
+/*
+ * Now that we are using mmap2 in srvclient, almost (*) the full 32
+ * bit offset is available.  The range of values is divided into two.
+ * The first part of the range, from FIRST_PHYSICAL_PFN to
+ * LAST_PHYSICAL_PFN, is for raw page mappings (VM_PFNMAP).  The
+ * resulting 43 bit (*) physical address range should be enough for
+ * the current range of processors we support.
+ *
+ * NB: (*) -- the above figures assume 4KB page size.  The offset
+ * argument to mmap2() is in units of 4,096 bytes regardless of page
+ * size.  Thus, we lose (PAGE_SHIFT-12) bits of resolution on other
+ * architectures.
+ *
+ * The second part of the range, from FIRST_SPECIAL_PFN to LAST_SPECIAL_PFN,
+ * is used for all other mappings.  These other mappings will always
+ * consist of pages with associated page structures, and need not
+ * represent a contiguous range of physical addresses.
+ *
+ */
 #define MMAP2_PGOFF_RESOLUTION (32-PAGE_SHIFT+12)
 #define RESERVED_PGOFF_BITS 1
 #define        MAX_MMAP_HANDLE         ((1UL<<(MMAP2_PGOFF_RESOLUTION-RESERVED_PGOFF_BITS))-1)
@@ -99,12 +145,19 @@ static struct proc_dir_entry *g_ProcMMap;
 #define        FIRST_SPECIAL_PFN       (LAST_PHYSICAL_PFN + 1)
 #define        LAST_SPECIAL_PFN        (FIRST_SPECIAL_PFN + MAX_MMAP_HANDLE)
 
-#else  
+#else  /* !defined(PVR_MAKE_ALL_PFNS_SPECIAL) */
 
 #if PAGE_SHIFT != 12
 #error This build variant has not yet been made non-4KB page-size aware
 #endif
 
+/*
+ * Since we no longer have to worry about clashes with the mmap
+ * offsets used for pure PFN mappings (VM_PFNMAP), there is greater
+ * freedom in choosing the mmap handles.  This is useful if the
+ * mmap offset space has to be shared with another driver component.
+ */
+
 #if defined(PVR_MMAP_OFFSET_BASE)
 #define        FIRST_SPECIAL_PFN       PVR_MMAP_OFFSET_BASE
 #else
@@ -117,21 +170,21 @@ static struct proc_dir_entry *g_ProcMMap;
 #define        MAX_MMAP_HANDLE         0x7fffffffUL
 #endif
 
-#endif 
+#endif /* !defined(PVR_MAKE_ALL_PFNS_SPECIAL) */
 
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
 static inline IMG_BOOL
 PFNIsPhysical(IMG_UINT32 pfn)
 {
-       
-       return ( (pfn <= LAST_PHYSICAL_PFN)) ? IMG_TRUE : IMG_FALSE;
+       /* Unsigned, no need to compare >=0 */
+       return (/*(pfn >= FIRST_PHYSICAL_PFN) &&*/ (pfn <= LAST_PHYSICAL_PFN)) ? IMG_TRUE : IMG_FALSE;
 }
 
 static inline IMG_BOOL
 PFNIsSpecial(IMG_UINT32 pfn)
 {
-       
-       return ((pfn >= FIRST_SPECIAL_PFN) ) ? IMG_TRUE : IMG_FALSE;
+       /* Unsigned, no need to compare <=MAX_UINT */
+       return ((pfn >= FIRST_SPECIAL_PFN) /*&& (pfn <= LAST_SPECIAL_PFN)*/) ? IMG_TRUE : IMG_FALSE;
 }
 #endif
 
@@ -168,6 +221,16 @@ HandleToMMapOffset(IMG_HANDLE hHandle)
 }
 
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
+/*
+ * Determine whether physical or special mappings will be used for
+ * a given memory area.  At present, this decision is made on
+ * whether the mapping represents a contiguous range of physical
+ * addresses, which is a requirement for raw page mappings (VM_PFNMAP).
+ * In the VMA structure for such a mapping, vm_pgoff is the PFN
+ * (page frame number, the physical address divided by the page size)
+ * of the first page in the VMA.  The second page is assumed to have
+ * PFN (vm_pgoff + 1), the third (vm_pgoff + 2) and so on.
+ */
 static inline IMG_BOOL
 LinuxMemAreaUsesPhysicalMap(LinuxMemArea *psLinuxMemArea)
 {
@@ -179,11 +242,18 @@ LinuxMemAreaUsesPhysicalMap(LinuxMemArea *psLinuxMemArea)
 static inline IMG_UINT32
 GetCurrentThreadID(IMG_VOID)
 {
-       
+       /*
+        * The PID is the thread ID, as each thread is a
+        * seperate process.
+        */
        return (IMG_UINT32)current->pid;
 }
 #endif
 
+/*
+ * Create an offset structure, which is used to hold per-process
+ * mmap data.
+ */
 static PKV_OFFSET_STRUCT
 CreateOffsetStruct(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32Offset, IMG_UINT32 ui32RealByteSize)
 {
@@ -215,14 +285,22 @@ CreateOffsetStruct(LinuxMemArea *psLinuxMemArea, IMG_UINT32 ui32Offset, IMG_UINT
 
     psOffsetStruct->ui32RealByteSize = ui32RealByteSize;
 
-    
+    /*
+     * We store the TID in case two threads within a process
+     * generate the same offset structure, and both end up on the
+     * list of structures waiting to be mapped, at the same time.
+     * This could happen if two sub areas within the same page are
+     * being mapped at the same time.
+     * The TID allows the mmap entry point to distinguish which
+     * mapping is being done by which thread.
+     */
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
     psOffsetStruct->ui32TID = GetCurrentThreadID();
 #endif
     psOffsetStruct->ui32PID = OSGetCurrentProcessIDKM();
 
 #if defined(DEBUG_LINUX_MMAP_AREAS)
-    
+    /* Extra entries to support proc filesystem debug info */
     psOffsetStruct->pszName = pszName;
 #endif
 
@@ -258,6 +336,17 @@ DestroyOffsetStruct(PKV_OFFSET_STRUCT psOffsetStruct)
 }
 
 
+/*
+ * There are no alignment constraints for mapping requests made by user
+ * mode Services.  For this, and potentially other reasons, the
+ * mapping created for a users request may look different to the
+ * original request in terms of size and alignment.
+ *
+ * This function determines an offset that the user can add to the mapping
+ * that is _actually_ created which will point to the memory they are
+ * _really_ interested in.
+ *
+ */
 static inline IMG_VOID
 DetermineUsersSizeAndByteOffset(LinuxMemArea *psLinuxMemArea,
                                IMG_UINT32 *pui32RealByteSize,
@@ -275,6 +364,33 @@ DetermineUsersSizeAndByteOffset(LinuxMemArea *psLinuxMemArea,
 }
 
 
+/*!
+ *******************************************************************************
+
+ @Function  PVRMMapOSMemHandleToMMapData
+
+ @Description
+
+ Determine various parameters needed to mmap a memory area, and to
+ locate the memory within the mapped area.
+
+ @input psPerProc : Per-process data.
+ @input hMHandle : Memory handle.
+ @input pui32MMapOffset : pointer to location for returned mmap offset.
+ @input pui32ByteOffset : pointer to location for returned byte offset.
+ @input pui32RealByteSize : pointer to location for returned real byte size.
+ @input pui32UserVaddr : pointer to location for returned user mode address.
+
+ @output pui32MMapOffset : points to mmap offset to be used in mmap2 sys call.
+ @output pui32ByteOffset : points to byte offset of start of memory
+                          within mapped area returned by mmap2.
+ @output pui32RealByteSize : points to size of area to be mapped.
+ @output pui32UserVAddr : points to user mode address of start of
+                         mapping, or 0 if it hasn't been mapped yet.
+
+ @Return PVRSRV_ERROR : PVRSRV_OK, or error code.
+
+ ******************************************************************************/
 PVRSRV_ERROR
 PVRMMapOSMemHandleToMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -310,28 +426,46 @@ PVRMMapOSMemHandleToMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
 
     psLinuxMemArea = (LinuxMemArea *)hOSMemHandle;
 
-    DetermineUsersSizeAndByteOffset(psLinuxMemArea,
-                                   pui32RealByteSize,
-                                   pui32ByteOffset);
+       /* Sparse mappings have to ask the BM for the virtual size */
+       if (psLinuxMemArea->hBMHandle)
+       {
+               *pui32RealByteSize = BM_GetVirtualSize(psLinuxMemArea->hBMHandle);
+               *pui32ByteOffset = 0;
+       }
+       else
+       {
+               DetermineUsersSizeAndByteOffset(psLinuxMemArea,
+                                                                               pui32RealByteSize,
+                                                                               pui32ByteOffset);
+       }
 
-    
+    /* Check whether this memory area has already been mapped */
     list_for_each_entry(psOffsetStruct, &psLinuxMemArea->sMMapOffsetStructList, sAreaItem)
     {
         if (psPerProc->ui32PID == psOffsetStruct->ui32PID)
         {
-
-          PVR_ASSERT(*pui32RealByteSize == psOffsetStruct->ui32RealByteSize);
-          
+                       if (!psLinuxMemArea->hBMHandle)
+                       {
+                               PVR_ASSERT(*pui32RealByteSize == psOffsetStruct->ui32RealByteSize);
+                       }
+          /*
+           * User mode locking is required to stop two threads racing to
+           * map the same memory area.  The lock should prevent a
+           * second thread retrieving mmap data for a given handle,
+           * before the first thread has done the mmap.
+           * Without locking, both threads may attempt the mmap,
+           * and one of them will fail.
+           */
           *pui32MMapOffset = psOffsetStruct->ui32MMapOffset;
           *pui32UserVAddr = psOffsetStruct->ui32UserVAddr;
-          psOffsetStruct->ui32RefCount++;
+          PVRSRVOffsetStructIncRef(psOffsetStruct);
 
           eError = PVRSRV_OK;
           goto exit_unlock;
         }
     }
 
-    
+    /* Memory area won't have been mapped yet */
     *pui32UserVAddr = 0;
 
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
@@ -356,18 +490,22 @@ PVRMMapOSMemHandleToMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
        goto exit_unlock;
     }
 
-    
+    /*
+    * Offset structures representing physical mappings are added to
+    * a list, so that they can be located when the memory area is mapped.
+    */
     list_add_tail(&psOffsetStruct->sMMapItem, &g_sMMapOffsetStructList);
 
     psOffsetStruct->bOnMMapList = IMG_TRUE;
 
-    psOffsetStruct->ui32RefCount++;
+    PVRSRVOffsetStructIncRef(psOffsetStruct);
 
     eError = PVRSRV_OK;
 
-       
-
-
+       /* Need to scale up the offset to counter the shifting that
+          is done in the mmap2() syscall, as it expects the pgoff
+          argument to be in units of 4,096 bytes irrespective of
+          page size */
        *pui32MMapOffset = *pui32MMapOffset << (PAGE_SHIFT - 12);
 
 exit_unlock:
@@ -377,6 +515,28 @@ exit_unlock:
 }
 
 
+/*!
+ *******************************************************************************
+
+ @Function  PVRMMapReleaseMMapData
+
+ @Description
+
+ Release mmap data.
+
+ @input psPerProc : Per-process data.
+ @input hMHandle : Memory handle.
+ @input pbMUnmap : pointer to location for munmap flag.
+ @input pui32UserVAddr : pointer to location for user mode address of mapping.
+ @input pui32ByteSize : pointer to location for size of mapping.
+
+ @Output pbMUnmap : points to flag that indicates whether an munmap is
+                   required.
+ @output pui32UserVAddr : points to user mode address to munmap.
+
+ @Return PVRSRV_ERROR : PVRSRV_OK, or error code.
+
+ ******************************************************************************/
 PVRSRV_ERROR
 PVRMMapReleaseMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -412,7 +572,7 @@ PVRMMapReleaseMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
 
     psLinuxMemArea = (LinuxMemArea *)hOSMemHandle;
 
-    
+    /* Find the offset structure */
     list_for_each_entry(psOffsetStruct, &psLinuxMemArea->sMMapOffsetStructList, sAreaItem)
     {
         if (psOffsetStruct->ui32PID == ui32PID)
@@ -424,7 +584,7 @@ PVRMMapReleaseMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
                goto exit_unlock;
            }
 
-           psOffsetStruct->ui32RefCount--;
+           PVRSRVOffsetStructDecRef(psOffsetStruct);
 
            *pbMUnmap = (IMG_BOOL)((psOffsetStruct->ui32RefCount == 0) && (psOffsetStruct->ui32UserVAddr != 0));
 
@@ -436,7 +596,7 @@ PVRMMapReleaseMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
         }
     }
 
-    
+    /* MMap data not found */
 #if defined (SUPPORT_SID_INTERFACE)
     PVR_DPF((PVR_DBG_ERROR, "%s: Mapping data not found for handle %x (memory area %p)", __FUNCTION__, hMHandle, psLinuxMemArea));
 #else
@@ -465,7 +625,11 @@ FindOffsetStructByOffset(IMG_UINT32 ui32Offset, IMG_UINT32 ui32RealByteSize)
         if (ui32Offset == psOffsetStruct->ui32MMapOffset && ui32RealByteSize == psOffsetStruct->ui32RealByteSize && psOffsetStruct->ui32PID == ui32PID)
         {
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
-           
+           /*
+            * If the offset is physical, make sure the thread IDs match,
+            * as different threads may be mapping different memory areas
+            * with the same offset.
+            */
            if (!PFNIsPhysical(ui32Offset) || psOffsetStruct->ui32TID == ui32TID)
 #endif
            {
@@ -478,6 +642,11 @@ FindOffsetStructByOffset(IMG_UINT32 ui32Offset, IMG_UINT32 ui32RealByteSize)
 }
 
 
+/*
+ * Map a memory area into user space.
+ * Note, the ui32ByteOffset is _not_ implicitly page aligned since
+ * LINUX_MEM_AREA_SUB_ALLOC LinuxMemAreas have no alignment constraints.
+ */
 static IMG_BOOL
 DoMapToUser(LinuxMemArea *psLinuxMemArea,
             struct vm_area_struct* ps_vma,
@@ -485,19 +654,33 @@ DoMapToUser(LinuxMemArea *psLinuxMemArea,
 {
     IMG_UINT32 ui32ByteSize;
 
+       if ((psLinuxMemArea->hBMHandle) && (ui32ByteOffset != 0))
+       {
+               /* Partial mapping of sparse allocations should never happen */
+               return IMG_FALSE;
+       }
+
     if (psLinuxMemArea->eAreaType == LINUX_MEM_AREA_SUB_ALLOC)
     {
-        return DoMapToUser(LinuxMemAreaRoot(psLinuxMemArea),            
+        return DoMapToUser(LinuxMemAreaRoot(psLinuxMemArea),           /* PRQA S 3670 */ /* allow recursion */
                     ps_vma,
                     psLinuxMemArea->uData.sSubAlloc.ui32ByteOffset + ui32ByteOffset);
     }
 
-    
+    /*
+     * Note that ui32ByteSize may be larger than the size of the memory
+     * area being mapped, as the former is a multiple of the page size.
+     */
     ui32ByteSize = ps_vma->vm_end - ps_vma->vm_start;
     PVR_ASSERT(ADDR_TO_PAGE_OFFSET(ui32ByteSize) == 0);
 
 #if defined (__sparc__)
-    
+    /*
+     * For LINUX_MEM_AREA_EXTERNAL_KV, we don't know where the address range
+     * we are being asked to map has come from, that is, whether it is memory
+     * or I/O.  For all architectures other than SPARC, there is no distinction.
+     * Since we don't currently support SPARC, we won't worry about it.
+     */
 #error "SPARC not supported"
 #endif
 
@@ -508,7 +691,13 @@ DoMapToUser(LinuxMemArea *psLinuxMemArea,
 
        PVR_ASSERT(LinuxMemAreaPhysIsContig(psLinuxMemArea));
        PVR_ASSERT(LinuxMemAreaToCpuPFN(psLinuxMemArea, ui32ByteOffset) == ps_vma->vm_pgoff);
-        
+        /*
+        * Since the memory is contiguous, we can map the whole range in one
+        * go .
+        */
+
+       PVR_ASSERT(psLinuxMemArea->hBMHandle == IMG_NULL);
+
        result = IO_REMAP_PFN_RANGE(ps_vma, ps_vma->vm_start, ps_vma->vm_pgoff, ui32ByteSize, ps_vma->vm_page_prot);
 
         if(result == 0)
@@ -521,27 +710,51 @@ DoMapToUser(LinuxMemArea *psLinuxMemArea,
 #endif
 
     {
-        
+        /*
+         * Memory may be non-contiguous, so we map the range page,
+        * by page.  Since VM_PFNMAP mappings are assumed to be physically
+        * contiguous, we can't legally use REMAP_PFN_RANGE (that is, we
+        * could, but the resulting VMA may confuse other bits of the kernel
+        * that attempt to interpret it).
+        * The only alternative is to use VM_INSERT_PAGE, which requires
+        * finding the page structure corresponding to each page, or
+        * if mixed maps are supported (VM_MIXEDMAP), vm_insert_mixed.
+        */
         IMG_UINT32 ulVMAPos;
        IMG_UINT32 ui32ByteEnd = ui32ByteOffset + ui32ByteSize;
        IMG_UINT32 ui32PA;
+       IMG_UINT32 ui32AdjustedPA = ui32ByteOffset;
 #if defined(PVR_MAKE_ALL_PFNS_SPECIAL)
        IMG_BOOL bMixedMap = IMG_FALSE;
 #endif
-       
+       /* First pass, validate the page frame numbers */
        for(ui32PA = ui32ByteOffset; ui32PA < ui32ByteEnd; ui32PA += PAGE_SIZE)
        {
-           IMG_UINT32 pfn =  LinuxMemAreaToCpuPFN(psLinuxMemArea, ui32PA);
+               IMG_UINT32 pfn;
+           IMG_BOOL bMapPage = IMG_TRUE;
 
-           if (!pfn_valid(pfn))
-           {
+               if (psLinuxMemArea->hBMHandle)
+               {
+                       if (!BM_MapPageAtOffset(psLinuxMemArea->hBMHandle, ui32PA))
+                       {
+                               bMapPage = IMG_FALSE;
+                       }
+               }
+
+               if (bMapPage)
+               {
+                       pfn =  LinuxMemAreaToCpuPFN(psLinuxMemArea, ui32AdjustedPA);
+                       if (!pfn_valid(pfn))
+                       {
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
-                PVR_DPF((PVR_DBG_ERROR,"%s: Error - PFN invalid: 0x%x", __FUNCTION__, pfn));
-                return IMG_FALSE;
+                                       PVR_DPF((PVR_DBG_ERROR,"%s: Error - PFN invalid: 0x%x", __FUNCTION__, pfn));
+                                       return IMG_FALSE;
 #else
-               bMixedMap = IMG_TRUE;
+                       bMixedMap = IMG_TRUE;
 #endif
-           }
+                       }
+                       ui32AdjustedPA += PAGE_SIZE;
+               }
        }
 
 #if defined(PVR_MAKE_ALL_PFNS_SPECIAL)
@@ -550,43 +763,58 @@ DoMapToUser(LinuxMemArea *psLinuxMemArea,
             ps_vma->vm_flags |= VM_MIXEDMAP;
        }
 #endif
-       
+       /* Second pass, get the page structures and insert the pages */
         ulVMAPos = ps_vma->vm_start;
+        ui32AdjustedPA = ui32ByteOffset;
        for(ui32PA = ui32ByteOffset; ui32PA < ui32ByteEnd; ui32PA += PAGE_SIZE)
        {
            IMG_UINT32 pfn;
            IMG_INT result;
+           IMG_BOOL bMapPage = IMG_TRUE;
+
+               if (psLinuxMemArea->hBMHandle)
+               {
+                       /* We have a sparse allocation, check if this page should be mapped */
+                       if (!BM_MapPageAtOffset(psLinuxMemArea->hBMHandle, ui32PA))
+                       {
+                               bMapPage = IMG_FALSE;
+                       }
+               }
 
-           pfn =  LinuxMemAreaToCpuPFN(psLinuxMemArea, ui32PA);
+               if (bMapPage)
+               {
+                       pfn =  LinuxMemAreaToCpuPFN(psLinuxMemArea, ui32AdjustedPA);
 
 #if defined(PVR_MAKE_ALL_PFNS_SPECIAL)
-           if (bMixedMap)
-           {
-               result = vm_insert_mixed(ps_vma, ulVMAPos, pfn);
-                if(result != 0)
-                {
-                    PVR_DPF((PVR_DBG_ERROR,"%s: Error - vm_insert_mixed failed (%d)", __FUNCTION__, result));
-                    return IMG_FALSE;
-                }
-           }
-           else
+                   if (bMixedMap)
+                   {
+                       result = vm_insert_mixed(ps_vma, ulVMAPos, pfn);
+                       if(result != 0)
+                       {
+                           PVR_DPF((PVR_DBG_ERROR,"%s: Error - vm_insert_mixed failed (%d)", __FUNCTION__, result));
+                           return IMG_FALSE;
+                       }
+                   }
+                   else
 #endif
-           {
-               struct page *psPage;
-
-               PVR_ASSERT(pfn_valid(pfn));
-
-               psPage = pfn_to_page(pfn);
-
-               result = VM_INSERT_PAGE(ps_vma,  ulVMAPos, psPage);
-                if(result != 0)
-                {
-                    PVR_DPF((PVR_DBG_ERROR,"%s: Error - VM_INSERT_PAGE failed (%d)", __FUNCTION__, result));
-                    return IMG_FALSE;
-                }
-           }
-            ulVMAPos += PAGE_SIZE;
-        }
+                   {
+                       struct page *psPage;
+       
+                       PVR_ASSERT(pfn_valid(pfn));
+       
+                       psPage = pfn_to_page(pfn);
+       
+                       result = VM_INSERT_PAGE(ps_vma,  ulVMAPos, psPage);
+                       if(result != 0)
+                       {
+                           PVR_DPF((PVR_DBG_ERROR,"%s: Error - VM_INSERT_PAGE failed (%d)", __FUNCTION__, result));
+                           return IMG_FALSE;
+                       }
+                   }
+                   ui32AdjustedPA += PAGE_SIZE;
+               }
+        ulVMAPos += PAGE_SIZE;
+    }
     }
 
     return IMG_TRUE;
@@ -597,10 +825,12 @@ static IMG_VOID
 MMapVOpenNoLock(struct vm_area_struct* ps_vma)
 {
     PKV_OFFSET_STRUCT psOffsetStruct = (PKV_OFFSET_STRUCT)ps_vma->vm_private_data;
-    PVR_ASSERT(psOffsetStruct != IMG_NULL)
-    psOffsetStruct->ui32Mapped++;
+
+    PVR_ASSERT(psOffsetStruct != IMG_NULL);
     PVR_ASSERT(!psOffsetStruct->bOnMMapList);
 
+    PVRSRVOffsetStructIncMapped(psOffsetStruct);
+
     if (psOffsetStruct->ui32Mapped > 1)
     {
        PVR_DPF((PVR_DBG_WARNING, "%s: Offset structure 0x%p is being shared across processes (psOffsetStruct->ui32Mapped: %u)", __FUNCTION__, psOffsetStruct, psOffsetStruct->ui32Mapped));
@@ -620,6 +850,9 @@ MMapVOpenNoLock(struct vm_area_struct* ps_vma)
 }
 
 
+/*
+ * Linux mmap open entry point.
+ */
 static void
 MMapVOpen(struct vm_area_struct* ps_vma)
 {
@@ -635,7 +868,7 @@ static IMG_VOID
 MMapVCloseNoLock(struct vm_area_struct* ps_vma)
 {
     PKV_OFFSET_STRUCT psOffsetStruct = (PKV_OFFSET_STRUCT)ps_vma->vm_private_data;
-    PVR_ASSERT(psOffsetStruct != IMG_NULL)
+    PVR_ASSERT(psOffsetStruct != IMG_NULL);
 
 #if defined(DEBUG_LINUX_MMAP_AREAS)
     PVR_DPF((PVR_DBG_MESSAGE,
@@ -648,7 +881,7 @@ MMapVCloseNoLock(struct vm_area_struct* ps_vma)
 #endif
 
     PVR_ASSERT(!psOffsetStruct->bOnMMapList);
-    psOffsetStruct->ui32Mapped--;
+    PVRSRVOffsetStructDecMapped(psOffsetStruct);
     if (psOffsetStruct->ui32Mapped == 0)
     {
        if (psOffsetStruct->ui32RefCount != 0)
@@ -662,6 +895,9 @@ MMapVCloseNoLock(struct vm_area_struct* ps_vma)
     ps_vma->vm_private_data = NULL;
 }
 
+/*
+ * Linux mmap close entry point.
+ */
 static void
 MMapVClose(struct vm_area_struct* ps_vma)
 {
@@ -672,20 +908,103 @@ MMapVClose(struct vm_area_struct* ps_vma)
     LinuxUnLockMutex(&g_sMMapMutex);
 }
 
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,26))
+/*
+ * This vma operation is used to read data from mmap regions. It is called
+ * by access_process_vm, which is called to handle PTRACE_PEEKDATA ptrace
+ * requests and reads from /proc/<pid>/mem.
+ */
+static int MMapVAccess(struct vm_area_struct *ps_vma, unsigned long addr,
+                                          void *buf, int len, int write)
+{
+    PKV_OFFSET_STRUCT psOffsetStruct;
+    LinuxMemArea *psLinuxMemArea;
+    unsigned long ulOffset;
+       int iRetVal = -EINVAL;
+       IMG_VOID *pvKernelAddr;
+
+       LinuxLockMutex(&g_sMMapMutex);
+
+       psOffsetStruct = (PKV_OFFSET_STRUCT)ps_vma->vm_private_data;
+       psLinuxMemArea = psOffsetStruct->psLinuxMemArea;
+       ulOffset = addr - ps_vma->vm_start;
+
+    if (ulOffset+len > psLinuxMemArea->ui32ByteSize)
+               /* Out of range. We shouldn't get here, because the kernel will do
+                  the necessary checks before calling access_process_vm. */
+               goto exit_unlock;
+
+       pvKernelAddr = LinuxMemAreaToCpuVAddr(psLinuxMemArea);
+
+       if (pvKernelAddr)
+       {
+               memcpy(buf, pvKernelAddr+ulOffset, len);
+               iRetVal = len;
+       }
+       else
+       {
+               IMG_UINT32 pfn, ui32OffsetInPage;
+               struct page *page;
+
+               pfn = LinuxMemAreaToCpuPFN(psLinuxMemArea, ulOffset);
+
+               if (!pfn_valid(pfn))
+                       goto exit_unlock;
+
+               page = pfn_to_page(pfn);
+               ui32OffsetInPage = ADDR_TO_PAGE_OFFSET(ulOffset);
+
+               if (ui32OffsetInPage+len > PAGE_SIZE)
+                       /* The region crosses a page boundary */
+                       goto exit_unlock;
+
+               pvKernelAddr = kmap(page);
+               memcpy(buf, pvKernelAddr+ui32OffsetInPage, len);
+               kunmap(page);
+
+               iRetVal = len;
+       }
+
+exit_unlock:
+       LinuxUnLockMutex(&g_sMMapMutex);
+    return iRetVal;
+}
+#endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,26) */
 
 static struct vm_operations_struct MMapIOOps =
 {
        .open=MMapVOpen,
-       .close=MMapVClose
+       .close=MMapVClose,
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,26))
+       .access=MMapVAccess,
+#endif
 };
 
 
+/*!
+ *******************************************************************************
+
+ @Function  PVRMMap
+
+ @Description
+
+ Driver mmap entry point.
+
+ @input pFile : unused.
+ @input ps_vma : pointer to linux memory area descriptor.
+
+ @Return 0, or Linux error code.
+
+ ******************************************************************************/
 int
 PVRMMap(struct file* pFile, struct vm_area_struct* ps_vma)
 {
-    IMG_UINT32 ui32ByteSize;
+    LinuxMemArea *psFlushMemArea = IMG_NULL;
     PKV_OFFSET_STRUCT psOffsetStruct;
+    IMG_UINT32 ui32ByteSize;
+    IMG_VOID *pvBase = IMG_NULL;
     int iRetVal = 0;
+    IMG_UINT32 ui32ByteOffset = 0;     /* Keep compiler happy */
 
     PVR_UNREFERENCED_PARAMETER(pFile);
 
@@ -700,17 +1019,23 @@ PVRMMap(struct file* pFile, struct vm_area_struct* ps_vma)
             ui32ByteSize, ui32ByteSize));
    
     psOffsetStruct = FindOffsetStructByOffset(ps_vma->vm_pgoff, ui32ByteSize);
+
     if (psOffsetStruct == IMG_NULL)
     {
 #if defined(SUPPORT_DRI_DRM)
         LinuxUnLockMutex(&g_sMMapMutex);
 
 #if !defined(SUPPORT_DRI_DRM_EXT)
-       
+        /* Pass unknown requests onto the DRM module */
         return drm_mmap(pFile, ps_vma);
 #else
-       
-       return -ENOENT;
+        /*
+         * Indicate to caller that the request is not for us.
+         * Do not return this error elsewhere in this function, as the
+         * caller may use it as a clue as to whether the mmap request
+         * should be passed on to another component (e.g. drm_mmap).
+         */
+        return -ENOENT;
 #endif
 #else
         PVR_UNREFERENCED_PARAMETER(pFile);
@@ -722,10 +1047,11 @@ PVRMMap(struct file* pFile, struct vm_area_struct* ps_vma)
 #endif
         goto unlock_and_return;
     }
+
     list_del(&psOffsetStruct->sMMapItem);
     psOffsetStruct->bOnMMapList = IMG_FALSE;
 
-    
+    /* Only support shared writeable mappings */
     if (((ps_vma->vm_flags & VM_WRITE) != 0) &&
         ((ps_vma->vm_flags & VM_SHARED) == 0))
     {
@@ -740,10 +1066,13 @@ PVRMMap(struct file* pFile, struct vm_area_struct* ps_vma)
     ps_vma->vm_flags |= VM_RESERVED;
     ps_vma->vm_flags |= VM_IO;
 
-    
+    /*
+     * Disable mremap because our nopage handler assumes all
+     * page requests have already been validated.
+     */
     ps_vma->vm_flags |= VM_DONTEXPAND;
     
-    
+    /* Don't allow mapping to be inherited across a process fork */
     ps_vma->vm_flags |= VM_DONTCOPY;
 
     ps_vma->vm_private_data = (void *)psOffsetStruct;
@@ -751,21 +1080,21 @@ PVRMMap(struct file* pFile, struct vm_area_struct* ps_vma)
     switch(psOffsetStruct->psLinuxMemArea->ui32AreaFlags & PVRSRV_HAP_CACHETYPE_MASK)
     {
         case PVRSRV_HAP_CACHED:
-            
+            /* This is the default, do nothing. */
             break;
         case PVRSRV_HAP_WRITECOMBINE:
-           ps_vma->vm_page_prot = PGPROT_WC(ps_vma->vm_page_prot);
+            ps_vma->vm_page_prot = PGPROT_WC(ps_vma->vm_page_prot);
             break;
         case PVRSRV_HAP_UNCACHED:
             ps_vma->vm_page_prot = PGPROT_UC(ps_vma->vm_page_prot);
             break;
         default:
             PVR_DPF((PVR_DBG_ERROR, "%s: unknown cache type", __FUNCTION__));
-           iRetVal = -EINVAL;
+            iRetVal = -EINVAL;
            goto unlock_and_return;
     }
     
-    
+    /* Install open and close handlers for ref-counting */
     ps_vma->vm_ops = &MMapIOOps;
     
     if(!DoMapToUser(psOffsetStruct->psLinuxMemArea, ps_vma, 0))
@@ -774,48 +1103,58 @@ PVRMMap(struct file* pFile, struct vm_area_struct* ps_vma)
         goto unlock_and_return;
     }
     
-    PVR_ASSERT(psOffsetStruct->ui32UserVAddr == 0)
+    PVR_ASSERT(psOffsetStruct->ui32UserVAddr == 0);
 
     psOffsetStruct->ui32UserVAddr = ps_vma->vm_start;
 
-    
+    /* Compute the flush region (if necessary) inside the mmap mutex */
     if(psOffsetStruct->psLinuxMemArea->bNeedsCacheInvalidate)
     {
-        IMG_UINT32 ui32RealByteSize, ui32ByteOffset;
-        IMG_VOID *pvBase;
+        IMG_UINT32 ui32DummyByteSize;
 
         DetermineUsersSizeAndByteOffset(psOffsetStruct->psLinuxMemArea,
-                                        &ui32RealByteSize,
+                                        &ui32DummyByteSize,
                                         &ui32ByteOffset);
 
-        ui32RealByteSize = psOffsetStruct->psLinuxMemArea->ui32ByteSize;
         pvBase = (IMG_VOID *)ps_vma->vm_start + ui32ByteOffset;
+        psFlushMemArea = psOffsetStruct->psLinuxMemArea;
 
-        OSInvalidateCPUCacheRangeKM(psOffsetStruct->psLinuxMemArea,
-                                    pvBase, ui32RealByteSize);
         psOffsetStruct->psLinuxMemArea->bNeedsCacheInvalidate = IMG_FALSE;
     }
 
-    
+    /* Call the open routine to increment the usage count */
     MMapVOpenNoLock(ps_vma);
-    
+
     PVR_DPF((PVR_DBG_MESSAGE, "%s: Mapped area at offset 0x%08lx\n",
              __FUNCTION__, ps_vma->vm_pgoff));
-    
+
 unlock_and_return:
     if (iRetVal != 0 && psOffsetStruct != IMG_NULL)
     {
-       DestroyOffsetStruct(psOffsetStruct);
+        DestroyOffsetStruct(psOffsetStruct);
     }
 
     LinuxUnLockMutex(&g_sMMapMutex);
-    
+
+    if(psFlushMemArea)
+    {
+        OSInvalidateCPUCacheRangeKM(psFlushMemArea, ui32ByteOffset, pvBase,
+                                                                       psFlushMemArea->ui32ByteSize);
+    }
+
     return iRetVal;
 }
 
 
 #if defined(DEBUG_LINUX_MMAP_AREAS)
 
+/*
+ * Lock MMap regions list (called on page start/stop while reading /proc/mmap)
+
+ * sfile : seq_file that handles /proc file
+ * start : TRUE if it's start, FALSE if it's stop
+ *  
+*/
 static void ProcSeqStartstopMMapRegistations(struct seq_file *sfile,IMG_BOOL start) 
 {
        if(start) 
@@ -829,6 +1168,16 @@ static void ProcSeqStartstopMMapRegistations(struct seq_file *sfile,IMG_BOOL sta
 }
 
 
+/*
+ * Convert offset (index from KVOffsetTable) to element 
+ * (called when reading /proc/mmap file)
+
+ * sfile : seq_file that handles /proc file
+ * off : index into the KVOffsetTable from which to print
+ *  
+ * returns void* : Pointer to element that will be dumped
+ *  
+*/
 static void* ProcSeqOff2ElementMMapRegistrations(struct seq_file *sfile, loff_t off)
 {
     LinuxMemArea *psLinuxMemArea;
@@ -854,12 +1203,28 @@ static void* ProcSeqOff2ElementMMapRegistrations(struct seq_file *sfile, loff_t
        return (void*)0;
 }
 
+/*
+ * Gets next MMap element to show. (called when reading /proc/mmap file)
+
+ * sfile : seq_file that handles /proc file
+ * el : actual element
+ * off : index into the KVOffsetTable from which to print
+ *  
+ * returns void* : Pointer to element to show (0 ends iteration)
+*/
 static void* ProcSeqNextMMapRegistrations(struct seq_file *sfile,void* el,loff_t off)
 {
        return ProcSeqOff2ElementMMapRegistrations(sfile,off);
 }
 
 
+/*
+ * Show MMap element (called when reading /proc/mmap file)
+
+ * sfile : seq_file that handles /proc file
+ * el : actual element
+ *  
+*/
 static void ProcSeqShowMMapRegistrations(struct seq_file *sfile, void *el)
 {
        KV_OFFSET_STRUCT *psOffsetStruct = (KV_OFFSET_STRUCT*)el;
@@ -933,6 +1298,20 @@ static void ProcSeqShowMMapRegistrations(struct seq_file *sfile, void *el)
 #endif
 
 
+/*!
+ *******************************************************************************
+
+ @Function  PVRMMapRegisterArea
+
+ @Description
+
+ Register a memory area with the mmap code.
+
+ @input psLinuxMemArea : pointer to memory area.
+
+ @Return PVRSRV_OK, or PVRSRV_ERROR.
+
+ ******************************************************************************/
 PVRSRV_ERROR
 PVRMMapRegisterArea(LinuxMemArea *psLinuxMemArea)
 {
@@ -951,7 +1330,7 @@ PVRMMapRegisterArea(LinuxMemArea *psLinuxMemArea)
 
     PVR_ASSERT(psLinuxMemArea->eAreaType != LINUX_MEM_AREA_SUB_ALLOC || LinuxMemAreaRoot(psLinuxMemArea)->eAreaType != LINUX_MEM_AREA_SUB_ALLOC);
 
-    
+    /* Check this mem area hasn't already been registered */
     if(psLinuxMemArea->bMMapRegistered)
     {
         PVR_DPF((PVR_DBG_ERROR, "%s: psLinuxMemArea 0x%p is already registered",
@@ -966,7 +1345,11 @@ PVRMMapRegisterArea(LinuxMemArea *psLinuxMemArea)
 
 #if defined(DEBUG_LINUX_MMAP_AREAS)
     g_ui32RegisteredAreas++;
-    
+    /*
+     * Sub memory areas are excluded from g_ui32TotalByteSize so that we
+     * don't count memory twice, once for the parent and again for sub
+     * allocationis.
+     */
     if (psLinuxMemArea->eAreaType != LINUX_MEM_AREA_SUB_ALLOC)
     {
         g_ui32TotalByteSize += psLinuxMemArea->ui32ByteSize;
@@ -982,6 +1365,20 @@ exit_unlock:
 }
 
 
+/*!
+ *******************************************************************************
+
+ @Function  PVRMMapRemoveRegisterArea
+
+ @Description
+
+ Unregister a memory area with the mmap code.
+
+ @input psLinuxMemArea : pointer to memory area.
+
+ @Return PVRSRV_OK, or PVRSRV_ERROR.
+
+ ******************************************************************************/
 PVRSRV_ERROR
 PVRMMapRemoveRegisteredArea(LinuxMemArea *psLinuxMemArea)
 {
@@ -997,12 +1394,19 @@ PVRMMapRemoveRegisteredArea(LinuxMemArea *psLinuxMemArea)
        if (psOffsetStruct->ui32Mapped != 0)
        {
             PVR_DPF((PVR_DBG_ERROR, "%s: psOffsetStruct 0x%p for memory area 0x0x%p is still mapped; psOffsetStruct->ui32Mapped %u",  __FUNCTION__, psOffsetStruct, psLinuxMemArea, psOffsetStruct->ui32Mapped));
+               dump_stack();
+               PVRSRVDumpRefCountCCB();
                eError = PVRSRV_ERROR_STILL_MAPPED;
                goto exit_unlock;
        }
        else
        {
-             
+             /*
+             * An offset structure is created when a call is made to get
+             * the mmap data for a physical mapping.  If the data is never
+             * used for mmap, we will be left with an umapped offset
+             * structure.
+             */
             PVR_DPF((PVR_DBG_WARNING, "%s: psOffsetStruct 0x%p was never mapped",  __FUNCTION__, psOffsetStruct));
        }
 
@@ -1031,6 +1435,20 @@ exit_unlock:
 }
 
 
+/*!
+ *******************************************************************************
+
+ @Function  LinuxMMapPerProcessConnect
+
+ @Description
+
+ Per-process mmap initialisation code.
+
+ @input psEnvPerProc : pointer to OS specific per-process data.
+
+ @Return PVRSRV_OK, or PVRSRV_ERROR.
+
+ ******************************************************************************/
 PVRSRV_ERROR
 LinuxMMapPerProcessConnect(PVRSRV_ENV_PER_PROCESS_DATA *psEnvPerProc)
 {
@@ -1039,6 +1457,18 @@ LinuxMMapPerProcessConnect(PVRSRV_ENV_PER_PROCESS_DATA *psEnvPerProc)
     return PVRSRV_OK;
 }
 
+/*!
+ *******************************************************************************
+
+ @Function  LinuxMMapPerProcessDisconnect
+
+ @Description
+
+ Per-process mmap deinitialisation code.
+
+ @input psEnvPerProc : pointer to OS specific per-process data.
+
+ ******************************************************************************/
 IMG_VOID
 LinuxMMapPerProcessDisconnect(PVRSRV_ENV_PER_PROCESS_DATA *psEnvPerProc)
 {
@@ -1070,6 +1500,20 @@ LinuxMMapPerProcessDisconnect(PVRSRV_ENV_PER_PROCESS_DATA *psEnvPerProc)
 }
 
 
+/*!
+ *******************************************************************************
+
+ @Function  LinuxMMapPerProcessHandleOptions
+
+ @Description
+
+ Set secure handle options required by mmap code.
+
+ @input psHandleBase : pointer to handle base.
+
+ @Return PVRSRV_OK, or PVRSRV_ERROR.
+
+ ******************************************************************************/
 PVRSRV_ERROR LinuxMMapPerProcessHandleOptions(PVRSRV_HANDLE_BASE *psHandleBase)
 {
     PVRSRV_ERROR eError;
@@ -1085,6 +1529,16 @@ PVRSRV_ERROR LinuxMMapPerProcessHandleOptions(PVRSRV_HANDLE_BASE *psHandleBase)
 }
 
 
+/*!
+ *******************************************************************************
+
+ @Function  PVRMMapInit
+
+ @Description
+
+ MMap initialisation code
+
+ ******************************************************************************/
 IMG_VOID
 PVRMMapInit(IMG_VOID)
 {
@@ -1104,7 +1558,7 @@ PVRMMapInit(IMG_VOID)
                                                  ProcSeqOff2ElementMMapRegistrations,
                                                  ProcSeqStartstopMMapRegistations
                                                 );
-#endif  
+#endif  /* defined(DEBUG_LINUX_MMAP_AREAS) */
     return;
 
 error:
@@ -1113,6 +1567,16 @@ error:
 }
 
 
+/*!
+ *******************************************************************************
+
+ @Function  PVRMMapCleanup
+
+ @Description
+
+ Mmap deinitialisation code
+
+ ******************************************************************************/
 IMG_VOID
 PVRMMapCleanup(IMG_VOID)
 {
@@ -1141,7 +1605,7 @@ PVRMMapCleanup(IMG_VOID)
 
 #if defined(DEBUG_LINUX_MMAP_AREAS)
     RemoveProcEntrySeq(g_ProcMMap);
-#endif 
+#endif /* defined(DEBUG_LINUX_MMAP_AREAS) */
 
     if(g_psMemmapCache)
     {
index 224e652..7140c13 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux mmap interface declaration
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined(__MMAP_H__)
 #define __MMAP_H__
 #include <linux/list.h>
 
 #if defined(VM_MIXEDMAP)
+/*
+ * Mixed maps allow us to avoid using raw PFN mappings (VM_PFNMAP) for
+ * pages without pages structures ("struct page"), giving us more
+ * freedom in choosing the mmap offset for mappings.  Mixed maps also
+ * allow both the mmap and the wrap code to be simplified somewhat.
+ */
 #define        PVR_MAKE_ALL_PFNS_SPECIAL
 #endif
 
 #include "perproc.h"
 #include "mm.h"
 
+/*
+ * This structure represents the relationship between an mmap2 file
+ * offset and a LinuxMemArea for a given process.
+ */
 typedef struct KV_OFFSET_STRUCT_TAG
 {
-    
+    /*
+     * Mapping count.  Incremented when the mapping is created, and
+     * if the mapping is inherited across a process fork.
+     */
     IMG_UINT32                 ui32Mapped;
 
-    
+    /*
+     * Offset to be passed to mmap2 to map the associated memory area
+     * into user space.  The offset may represent the page frame number
+     * of the first page in the area (if the area is physically
+     * contiguous), or it may represent the secure handle associated
+     * with the area.
+     */
     IMG_UINT32                  ui32MMapOffset;
     
     IMG_UINT32                 ui32RealByteSize;
 
-    
+    /* Memory area associated with this offset structure */
     LinuxMemArea                *psLinuxMemArea;
     
 #if !defined(PVR_MAKE_ALL_PFNS_SPECIAL)
-    
+    /* ID of the thread that owns this structure */
     IMG_UINT32                 ui32TID;
 #endif
 
-    
+    /* ID of the process that owns this structure */
     IMG_UINT32                 ui32PID;
 
-    
+    /*
+     * For offsets that represent actual page frame numbers, this structure
+     * is temporarily put on a list so that it can be found from the
+     * driver mmap entry point.  This flag indicates the structure is
+     * on the list.
+     */
     IMG_BOOL                   bOnMMapList;
 
-    
+    /* Reference count for this structure */
     IMG_UINT32                 ui32RefCount;
 
-    
+    /*
+     * User mode address of start of mapping.  This is not necessarily the
+     * first user mode address of the memory area.
+     */
     IMG_UINT32                 ui32UserVAddr;
 
-    
+    /* Extra entries to support proc filesystem debug info */
 #if defined(DEBUG_LINUX_MMAP_AREAS)
     const IMG_CHAR             *pszName;
 #endif
     
-   
+   /* List entry field for MMap list */
    struct list_head            sMMapItem;
 
-   
+   /* List entry field for per-memory area list */
    struct list_head            sAreaItem;
 }KV_OFFSET_STRUCT, *PKV_OFFSET_STRUCT;
 
 
 
+/*!
+ *******************************************************************************
+ * @Function Mmap initialisation code
+ ******************************************************************************/
 IMG_VOID PVRMMapInit(IMG_VOID);
 
 
+/*!
+ *******************************************************************************
+ * @Function Mmap de-initialisation code
+ ******************************************************************************/
 IMG_VOID PVRMMapCleanup(IMG_VOID);
 
 
+/*!
+ *******************************************************************************
+ * @Function Registers a memory area with the mmap code
+ *          
+ * @Input psLinuxMemArea
+ *
+ * @Return PVRSRV_ERROR status
+ ******************************************************************************/
 PVRSRV_ERROR PVRMMapRegisterArea(LinuxMemArea *psLinuxMemArea);
 
 
+/*!
+ *******************************************************************************
+ * @Function Unregisters a memory area from the mmap code
+ *
+ * @Input psLinuxMemArea
+ *
+ * @Return PVRSRV_ERROR status
+ ******************************************************************************/
 PVRSRV_ERROR PVRMMapRemoveRegisteredArea(LinuxMemArea *psLinuxMemArea);
 
 
+/*!
+ ******************************************************************************
+ * @Function When a userspace services client, requests to map a memory
+ *           area to userspace, this function validates the request and
+ *           returns the details that the client must use when calling mmap(2).
+ *
+ * @Input psPerProc            Per process data.
+ * @Input hMHandle              Handle associated with the memory to map.
+ *                             This is a (secure) handle to the OS specific
+ *                             memory handle structure (hOSMemHandle), or
+ *                             a handle to a structure that contains the 
+ *                             memory handle.
+ * @Output pui32MMapOffset      The page aligned offset that the client must
+ *                             pass to the mmap2 system call.
+ * @Output pui32ByteOffset       The real mapping that will be created for the
+ *                             services client may have a different
+ *                             size/alignment from it request. This offset
+ *                             is returned to the client and should be added
+ *                             to virtual address returned from mmap2 to get
+ *                             the first address corresponding to its request.
+ * @Output pui32RealByteOffset   The size that the mapping will really be,
+ *                             that the client must also pass to mmap/munmap.
+ *
+ * @Output pui32UserVAddr      Pointer to returned user mode address of 
+ *                             mapping.
+ * @Return PVRSRV_ERROR
+ ******************************************************************************/
 PVRSRV_ERROR PVRMMapOSMemHandleToMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
 #if defined (SUPPORT_SID_INTERFACE)
                                           IMG_SID     hMHandle,
@@ -104,6 +197,21 @@ PVRSRV_ERROR PVRMMapOSMemHandleToMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
                                           IMG_UINT32 *pui32RealByteSize,
                                           IMG_UINT32 *pui32UserVAddr);
 
+/*!
+ *******************************************************************************
+
+ @Function Release mmap data.
+
+ @Input psPerProc            Per-process data.
+ @Input hMHandle             Memory handle.
+
+ @Output pbMUnmap            Flag that indicates whether an munmap is
+                            required.
+ @Output pui32RealByteSize   Location for size of mapping.
+ @Output pui32UserVAddr      User mode address to munmap.
+
+ @Return PVRSRV_ERROR
+ ******************************************************************************/
 PVRSRV_ERROR
 PVRMMapReleaseMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
 #if defined (SUPPORT_SID_INTERFACE)
@@ -115,8 +223,18 @@ PVRMMapReleaseMMapData(PVRSRV_PER_PROCESS_DATA *psPerProc,
                                IMG_UINT32 *pui32RealByteSize,
                                 IMG_UINT32 *pui32UserVAddr);
 
+/*!
+ *******************************************************************************
+ * @Function driver mmap entry point
+ * 
+ * @Input pFile : user file structure
+ *
+ * @Input ps_vma : vm area structure
+ * 
+ * @Return 0 for success, -errno for failure.
+ ******************************************************************************/
 int PVRMMap(struct file* pFile, struct vm_area_struct* ps_vma);
 
 
-#endif 
+#endif /* __MMAP_H__ */
 
index 1a96e7c..ea4b5e3 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux module setup
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 
 #endif
 #endif
 
-#if defined(SUPPORT_DRI_DRM)
+#if defined(SUPPORT_DRI_DRM) && !defined(SUPPORT_DRI_DRM_PLUGIN)
 #define        PVR_MOD_STATIC
 #else
-       
+       /*
+        * For LDM drivers, define PVR_LDM_MODULE to indicate generic LDM
+        * support is required, besides indicating the exact support
+        * required (e.g. platform, or PCI device).
+        */
        #if defined(LDM_PLATFORM)
                #define PVR_LDM_PLATFORM_MODULE
+               #define PVR_LDM_DEVICE_CLASS
                #define PVR_LDM_MODULE
        #else
                #if defined(LDM_PCI)
+                       #define PVR_LDM_DEVICE_CLASS
                        #define PVR_LDM_PCI_MODULE
                        #define PVR_LDM_MODULE
+               #else
+                       #if defined(SYS_SHARES_WITH_3PKM)
+                               #define PVR_LDM_DEVICE_CLASS
+                       #endif
                #endif
        #endif
 #define        PVR_MOD_STATIC  static
 
 #if defined(PVR_LDM_PLATFORM_MODULE)
 #include <linux/platform_device.h>
-#endif 
+#endif /* PVR_LDM_PLATFORM_MODULE */
 
 #if defined(PVR_LDM_PCI_MODULE)
 #include <linux/pci.h>
-#endif 
+#endif /* PVR_LDM_PCI_MODULE */
+
+#if defined(PVR_LDM_DEVICE_CLASS)
+#include <linux/device.h>
+#endif /* PVR_LDM_DEVICE_CLASS */
 
 #if defined(DEBUG) && defined(PVR_MANUAL_POWER_CONTROL)
 #include <asm/uaccess.h>
 #include "private_data.h"
 #include "lock.h"
 #include "linkage.h"
+#include "buffer_manager.h"
 
 #if defined(SUPPORT_DRI_DRM)
 #include "pvr_drm.h"
 #endif
-#define DRVNAME                PVRSRV_MODNAME
+/*
+ * DRVNAME is the name we use to register our driver.
+ * DEVNAME is the name we use to register actual device nodes.
+ */
+#if defined(PVR_LDM_MODULE)
+//#define      DRVNAME         PVR_LDM_DRIVER_REGISTRATION_NAME
+#define        DRVNAME         PVRSRV_MODNAME  
+#endif
 #define DEVNAME                PVRSRV_MODNAME
 
 #if defined(SUPPORT_DRI_DRM)
 #define PRIVATE_DATA(pFile) ((pFile)->private_data)
 #endif
 
+/*
+ * This is all module configuration stuff required by the linux kernel.
+ */
 MODULE_SUPPORTED_DEVICE(DEVNAME);
 
 #if defined(PVRSRV_NEED_PVR_DPF)
@@ -119,19 +159,40 @@ MODULE_SUPPORTED_DEVICE(DEVNAME);
 extern IMG_UINT32 gPVRDebugLevel;
 module_param(gPVRDebugLevel, uint, 0644);
 MODULE_PARM_DESC(gPVRDebugLevel, "Sets the level of debug output (default 0x7)");
-#endif 
+#endif /* defined(PVRSRV_NEED_PVR_DPF) */
+
+#if defined(CONFIG_ION_OMAP)
+#include <linux/ion.h>
+#include <linux/omap_ion.h>
+extern struct ion_device *omap_ion_device;
+struct ion_client *gpsIONClient;
+EXPORT_SYMBOL(gpsIONClient);
+#endif /* defined(CONFIG_ION_OMAP) */
 
+/* PRQA S 3207 2 */ /* ignore 'not used' warning */
 EXPORT_SYMBOL(PVRGetDisplayClassJTable);
 EXPORT_SYMBOL(PVRGetBufferClassJTable);
 
-#if defined(PVR_LDM_MODULE)
+#if defined(PVR_LDM_DEVICE_CLASS) && !defined(SUPPORT_DRI_DRM)
+/*
+ * Device class used for /sys entries (and udev device node creation)
+ */
 static struct class *psPvrClass;
 #endif
 
 #if !defined(SUPPORT_DRI_DRM)
+/*
+ * This is the major number we use for all nodes in /dev.
+ */
 static int AssignedMajorNumber;
 
+/*
+ * These are the operations that will be associated with the device node
+ * we create.
+ *
+ * With gcc -W, specifying only the non-null members produces "missing
+ * initializer" warnings.
+*/
 static int PVRSRVOpen(struct inode* pInode, struct file* pFile);
 static int PVRSRVRelease(struct inode* pInode, struct file* pFile);
 
@@ -147,6 +208,7 @@ static struct file_operations pvrsrv_fops =
 
 PVRSRV_LINUX_MUTEX gPVRSRVLock;
 
+/* PID of process being released */
 IMG_UINT32 gui32ReleasePID;
 
 #if defined(DEBUG) && defined(PVR_MANUAL_POWER_CONTROL)
@@ -158,12 +220,15 @@ static IMG_UINT32 gPVRPowerLevel;
 #if defined(PVR_LDM_PLATFORM_MODULE)
 #define        LDM_DEV struct platform_device
 #define        LDM_DRV struct platform_driver
-#endif 
+#endif /*PVR_LDM_PLATFORM_MODULE */
 
 #if defined(PVR_LDM_PCI_MODULE)
 #define        LDM_DEV struct pci_dev
 #define        LDM_DRV struct pci_driver
-#endif 
+#endif /* PVR_LDM_PCI_MODULE */
+/*
+ * This is the driver interface we support.  
+ */
 #if defined(PVR_LDM_PLATFORM_MODULE)
 static int PVRSRVDriverRemove(LDM_DEV *device);
 static int PVRSRVDriverProbe(LDM_DEV *device);
@@ -177,6 +242,7 @@ static void PVRSRVDriverShutdown(LDM_DEV *device);
 static int PVRSRVDriverResume(LDM_DEV *device);
 
 #if defined(PVR_LDM_PCI_MODULE)
+/* This structure is used by the Linux module code */
 struct pci_device_id powervr_id_table[] __devinitdata = {
        {PCI_DEVICE(SYS_SGX_DEV_VENDOR_ID, SYS_SGX_DEV_DEVICE_ID)},
 #if defined (SYS_SGX_DEV1_DEVICE_ID)
@@ -236,6 +302,22 @@ static struct platform_device powervr_device = {
 };
 #endif
 
+/*!
+******************************************************************************
+
+ @Function             PVRSRVDriverProbe
+
+ @Description
+
+ See whether a given device is really one we can drive.  The platform bus
+ handler has already established that we should be able to service this device
+ because of the name match.  We probably don't need to do anything else.
+
+ @input pDevice - the device for which a probe is requested
+
+ @Return 0 for success or <0 for an error.
+
+*****************************************************************************/
 #if defined(PVR_LDM_PLATFORM_MODULE)
 static int PVRSRVDriverProbe(LDM_DEV *pDevice)
 #endif
@@ -247,29 +329,66 @@ static int __devinit PVRSRVDriverProbe(LDM_DEV *pDevice, const struct pci_device
 
        PVR_TRACE(("PVRSRVDriverProbe(pDevice=%p)", pDevice));
 
-#if 0
-       
+#if 0   /* INTEGRATION_POINT */
+       /* Some systems require device-specific system initialisation.
+        * E.g. this lets the OS track a device's dependencies on various
+        * system hardware.
+        *
+        * Note: some systems use this to enable HW that SysAcquireData
+        * will depend on, therefore it must be called first.
+        */
        if (PerDeviceSysInitialise((IMG_PVOID)pDevice) != PVRSRV_OK)
        {
                return -EINVAL;
        }
 #endif 
-       
+       /* SysInitialise only designed to be called once.
+        */
        psSysData = SysAcquireDataNoCheck();
-       if ( psSysData == IMG_NULL)
+       if (psSysData == IMG_NULL)
        {
                gpsPVRLDMDev = pDevice;
-
                if (SysInitialise() != PVRSRV_OK)
                {
                        return -ENODEV;
                }
        }
 
+#if defined(CONFIG_ION_OMAP)
+       gpsIONClient = ion_client_create(omap_ion_device,
+                                                                        1 << ION_HEAP_TYPE_CARVEOUT |
+                                                                        1 << OMAP_ION_HEAP_TYPE_TILER,
+                                                                        "pvr");
+       if (IS_ERR_OR_NULL(gpsIONClient))
+       {
+               PVR_DPF((PVR_DBG_ERROR, "PVRSRVDriverProbe: Couldn't create ion client"));
+               return PTR_ERR(gpsIONClient);
+       }
+#endif /* defined(CONFIG_ION_OMAP) */
+
        return 0;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             PVRSRVDriverRemove
+
+ @Description
+
+ This call is the opposite of the probe call: it is called when the device is
+ being removed from the driver's control.  See the file $KERNELDIR/drivers/
+ base/bus.c:device_release_driver() for the call to this function.
+
+ This is the correct place to clean up anything our driver did while it was
+ asoociated with the device.
+
+ @input pDevice - the device for which driver detachment is happening
+
+ @Return 0 for success or <0 for an error.
+
+*****************************************************************************/
 #if defined (PVR_LDM_PLATFORM_MODULE)
 static int PVRSRVDriverRemove(LDM_DEV *pDevice)
 #endif
@@ -281,6 +400,11 @@ static void __devexit PVRSRVDriverRemove(LDM_DEV *pDevice)
 
        PVR_TRACE(("PVRSRVDriverRemove(pDevice=%p)", pDevice));
 
+#if defined(CONFIG_ION_OMAP)
+       ion_client_destroy(gpsIONClient);
+       gpsIONClient = IMG_NULL;
+#endif
+
        SysAcquireData(&psSysData);
        
 #if defined(DEBUG) && defined(PVR_MANUAL_POWER_CONTROL)
@@ -296,7 +420,8 @@ static void __devexit PVRSRVDriverRemove(LDM_DEV *pDevice)
 
        gpsPVRLDMDev = IMG_NULL;
 
-#if 0
+#if 0   /* INTEGRATION_POINT */
+       /* See previous integration point for details. */
        if (PerDeviceSysDeInitialise((IMG_PVOID)pDevice) != PVRSRV_OK)
        {
                return -EINVAL;
@@ -310,59 +435,224 @@ static void __devexit PVRSRVDriverRemove(LDM_DEV *pDevice)
        return;
 #endif
 }
-#endif 
+#endif /* defined(PVR_LDM_MODULE) */
 
 
+#if defined(PVR_LDM_MODULE) || defined(SUPPORT_DRI_DRM)
+static PVRSRV_LINUX_MUTEX gsPMMutex;
+static IMG_BOOL bDriverIsSuspended;
+static IMG_BOOL bDriverIsShutdown;
+#endif
+
 #if defined(PVR_LDM_MODULE) || defined(PVR_DRI_DRM_PLATFORM_DEV)
+/*!
+******************************************************************************
+
+ @Function             PVRSRVDriverShutdown
+
+ @Description
+
+ Suspend device operation for system shutdown.  This is called as part of the
+ system halt/reboot process.  The driver is put into a quiescent state by 
+ setting the power state to D3.
+
+ @input pDevice - the device for which shutdown is requested
+
+ @Return nothing
+
+*****************************************************************************/
+#if defined(SUPPORT_DRI_DRM) && !defined(PVR_DRI_DRM_PLATFORM_DEV) && \
+       !defined(SUPPORT_DRI_DRM_PLUGIN)
+void PVRSRVDriverShutdown(struct drm_device *pDevice)
+#else
 PVR_MOD_STATIC void PVRSRVDriverShutdown(LDM_DEV *pDevice)
+#endif
 {
        PVR_TRACE(("PVRSRVDriverShutdown(pDevice=%p)", pDevice));
 
-       (void) PVRSRVSetPowerStateKM(PVRSRV_SYS_POWER_STATE_D3);
+       LinuxLockMutex(&gsPMMutex);
+
+       if (!bDriverIsShutdown && !bDriverIsSuspended)
+       {
+               /*
+                * Take the bridge mutex, and never release it, to stop
+                * processes trying to use the driver after it has been
+                * shutdown.
+                */
+               LinuxLockMutex(&gPVRSRVLock);
+
+               (void) PVRSRVSetPowerStateKM(PVRSRV_SYS_POWER_STATE_D3);
+       }
+
+       bDriverIsShutdown = IMG_TRUE;
+
+       /* The bridge mutex is held on exit */
+       LinuxUnLockMutex(&gsPMMutex);
 }
 
-#endif 
+#endif /* defined(PVR_LDM_MODULE) || defined(PVR_DRI_DRM_PLATFORM_DEV) */
 
 
 #if defined(PVR_LDM_MODULE) || defined(SUPPORT_DRI_DRM)
-#if defined(SUPPORT_DRI_DRM) && !defined(PVR_DRI_DRM_PLATFORM_DEV)
+/*!
+******************************************************************************
+
+ @Function             PVRSRVDriverSuspend
+
+ @Description
+
+ For 2.6 kernels:
+ Suspend device operation.  We always get three calls to this regardless of
+ the state (D1-D3) chosen.  The order is SUSPEND_DISABLE, SUSPEND_SAVE_STATE
+ then SUSPEND_POWER_DOWN.  We take action as soon as we get the disable call,
+ the other states not being handled by us yet.
+
+ For MontaVista 2.4 kernels:
+ This call gets made once only when someone does something like
+
+       # echo -e -n "suspend powerdown 0" >/sys.devices/legacy/pvrsrv0/power
+
+ The 3rd, numeric parameter (0) in the above has no relevence and is not
+ passed into us.  The state parameter is always zero and the level parameter
+ is always SUSPEND_POWER_DOWN.  Vive la difference!
+
+ @input pDevice - the device for which resume is requested
+
+ @Return 0 for success or <0 for an error.
+
+*****************************************************************************/
+#if defined(SUPPORT_DRI_DRM) && !defined(PVR_DRI_DRM_PLATFORM_DEV) && \
+       !defined(SUPPORT_DRI_DRM_PLUGIN)
+#if defined(SUPPORT_DRM_MODESET)
+int PVRSRVDriverSuspend(struct pci_dev *pDevice, pm_message_t state)
+#else
 int PVRSRVDriverSuspend(struct drm_device *pDevice, pm_message_t state)
+#endif
 #else
 PVR_MOD_STATIC int PVRSRVDriverSuspend(LDM_DEV *pDevice, pm_message_t state)
 #endif
 {
+       int res = 0;
 #if !(defined(DEBUG) && defined(PVR_MANUAL_POWER_CONTROL) && !defined(SUPPORT_DRI_DRM))
        PVR_TRACE(( "PVRSRVDriverSuspend(pDevice=%p)", pDevice));
 
-       if (PVRSRVSetPowerStateKM(PVRSRV_SYS_POWER_STATE_D3) != PVRSRV_OK)
+       LinuxLockMutex(&gsPMMutex);
+
+       if (!bDriverIsSuspended && !bDriverIsShutdown)
        {
-               return -EINVAL;
+               LinuxLockMutex(&gPVRSRVLock);
+
+               if (PVRSRVSetPowerStateKM(PVRSRV_SYS_POWER_STATE_D3) == PVRSRV_OK)
+               {
+                       /* The bridge mutex will be held until we resume */
+                       bDriverIsSuspended = IMG_TRUE;
+               }
+               else
+               {
+                       LinuxUnLockMutex(&gPVRSRVLock);
+                       res = -EINVAL;
+               }
        }
+
+       LinuxUnLockMutex(&gsPMMutex);
 #endif
-       return 0;
+       return res;
 }
 
 
-#if defined(SUPPORT_DRI_DRM) && !defined(PVR_DRI_DRM_PLATFORM_DEV)
+/*!
+******************************************************************************
+
+ @Function             PVRSRVDriverResume
+
+ @Description
+
+ Resume device operation following a lull due to earlier suspension.  It is
+ implicit we're returning to D0 (fully operational) state.  We always get three
+ calls to this using level thus: RESUME_POWER_ON, RESUME_RESTORE_STATE then
+ RESUME_ENABLE.  On 2.6 kernels We don't do anything until we get the enable
+ call; on the MontaVista set-up we only ever get the RESUME_POWER_ON call.
+
+ @input pDevice - the device for which resume is requested
+
+ @Return 0 for success or <0 for an error.
+
+*****************************************************************************/
+#if defined(SUPPORT_DRI_DRM) && !defined(PVR_DRI_DRM_PLATFORM_DEV) && \
+       !defined(SUPPORT_DRI_DRM_PLUGIN)
+#if defined(SUPPORT_DRM_MODESET)
+int PVRSRVDriverResume(struct pci_dev *pDevice)
+#else
 int PVRSRVDriverResume(struct drm_device *pDevice)
+#endif
 #else
 PVR_MOD_STATIC int PVRSRVDriverResume(LDM_DEV *pDevice)
 #endif
 {
+       int res = 0;
 #if !(defined(DEBUG) && defined(PVR_MANUAL_POWER_CONTROL) && !defined(SUPPORT_DRI_DRM))
        PVR_TRACE(("PVRSRVDriverResume(pDevice=%p)", pDevice));
 
-       if (PVRSRVSetPowerStateKM(PVRSRV_SYS_POWER_STATE_D0) != PVRSRV_OK)
+       LinuxLockMutex(&gsPMMutex);
+
+       if (bDriverIsSuspended && !bDriverIsShutdown)
        {
-               return -EINVAL;
+               if (PVRSRVSetPowerStateKM(PVRSRV_SYS_POWER_STATE_D0) == PVRSRV_OK)
+               {
+                       bDriverIsSuspended = IMG_FALSE;
+                       LinuxUnLockMutex(&gPVRSRVLock);
+               }
+               else
+               {
+                       /* The bridge mutex is not released on failure */
+                       res = -EINVAL;
+               }
        }
+
+       LinuxUnLockMutex(&gsPMMutex);
 #endif
-       return 0;
+       return res;
 }
-#endif 
+#endif /* defined(PVR_LDM_MODULE) || defined(SUPPORT_DRI_DRM) */
 
 
 #if defined(DEBUG) && defined(PVR_MANUAL_POWER_CONTROL) && !defined(SUPPORT_DRI_DRM)
+/*
+ * If PVR_LDM_PCI_MODULE is defined (and PVR_MANUAL_POWER_CONTROL is *NOT* defined),
+ * the device can be suspended and resumed without suspending/resuming the
+ * system, by writing values into the power/state sysfs file for the device.
+ * To suspend:
+ *     echo -n 2 > power/state
+ * To Resume:
+ *     echo -n 0 > power/state
+ *
+ * The problem with this approach is that the device is usually left
+ * powered up; it is the responsibility of the bus driver to remove
+ * the power.
+ *
+ * Defining PVR_MANUAL_POWER_CONTROL is intended to make it easier to
+ * debug power management issues, especially when power is really removed
+ * from the device.  It is easier to debug the driver if it is not being
+ * suspended/resumed with the rest of the system.
+ *
+ * When PVR_MANUAL_POWER_CONTROL is defined, the following proc entry is
+ * created:
+ *     /proc/pvr/power_control
+ * The driver suspend/resume entry points defined below no longer suspend or
+ * resume the device.  To suspend the device, type the following:
+ *     echo 2 > /proc/pvr/power_control
+ * To resume the device, type:
+ *     echo 0 > /proc/pvr/power_control
+ * 
+ * The following example shows how to suspend/resume the device independently
+ * of the rest of the system.
+ * Suspend the device:
+ *     echo 2 > /proc/pvr/power_control
+ * Suspend the system.  Then you should be able to suspend and resume
+ * as normal.  To resume the device type the following:
+ *     echo 0 > /proc/pvr/power_control
+ */
+
 IMG_INT PVRProcSetPowerLevel(struct file *file, const IMG_CHAR *buffer, IMG_UINT32 count, IMG_VOID *data)
 {
        IMG_CHAR data_buffer[2];
@@ -409,6 +699,23 @@ void ProcSeqShowPowerLevel(struct seq_file *sfile,void* el)
 
 #endif
 
+/*!
+******************************************************************************
+
+ @Function             PVRSRVOpen
+
+ @Description
+
+ Release access the PVR services node - called when a file is closed, whether
+ at exit or using close(2) system call.
+
+ @input pInode - the inode for the file being openeded
+
+ @input pFile - the file handle data for the actual file being opened
+
+ @Return 0 for success or <0 for an error.
+
+*****************************************************************************/
 #if defined(SUPPORT_DRI_DRM)
 int PVRSRVOpen(struct drm_device unref__ *dev, struct drm_file *pFile)
 #else
@@ -469,6 +776,23 @@ err_unlock:
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             PVRSRVRelease
+
+ @Description
+
+ Release access the PVR services node - called when a file is closed, whether
+ at exit or using close(2) system call.
+
+ @input pInode - the inode for the file being released
+
+ @input pFile - the file handle data for the actual file being released
+
+ @Return 0 for success or <0 for an error.
+
+*****************************************************************************/
 #if defined(SUPPORT_DRI_DRM)
 void PVRSRVRelease(void *pvPrivData)
 #else
@@ -476,6 +800,7 @@ static int PVRSRVRelease(struct inode unref__ * pInode, struct file *pFile)
 #endif
 {
        PVRSRV_FILE_PRIVATE_DATA *psPrivateData;
+       int err = 0;
 
        LinuxLockMutex(&gPVRSRVLock);
 
@@ -490,7 +815,40 @@ static int PVRSRVRelease(struct inode unref__ * pInode, struct file *pFile)
                list_del(&psPrivateData->sDRMAuthListItem);
 #endif
 
-               
+               if(psPrivateData->hKernelMemInfo)
+               {
+                       PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo;
+
+                       /* Look up the meminfo we just exported */
+                       if(PVRSRVLookupHandle(KERNEL_HANDLE_BASE,
+                                                                 (IMG_PVOID *)&psKernelMemInfo,
+                                                                 psPrivateData->hKernelMemInfo,
+                                                                 PVRSRV_HANDLE_TYPE_MEM_INFO) != PVRSRV_OK)
+                       {
+                               PVR_DPF((PVR_DBG_ERROR, "%s: Failed to look up export handle", __FUNCTION__));
+                               err = -EFAULT;
+                               goto err_unlock;
+                       }
+
+                       /* Tell the XProc about the export if required */
+                       if (psKernelMemInfo->sShareMemWorkaround.bInUse)
+                       {
+                               BM_XProcIndexRelease(psKernelMemInfo->sShareMemWorkaround.ui32ShareIndex);
+                       }
+
+                       /* This drops the psMemInfo refcount bumped on export */
+                       if(FreeMemCallBackCommon(psKernelMemInfo, 0,
+                                                                        PVRSRV_FREE_CALLBACK_ORIGIN_EXTERNAL) != PVRSRV_OK)
+                       {
+                               PVR_DPF((PVR_DBG_ERROR, "%s: FreeMemCallBackCommon failed", __FUNCTION__));
+                               err = -EFAULT;
+                               goto err_unlock;
+                       }
+               }
+
+               /* Usually this is the same as OSGetCurrentProcessIDKM(),
+                * but not necessarily (e.g. fork(), child closes last..)
+                */
                gui32ReleasePID = psPrivateData->ui32OpenPID;
                PVRSRVProcessDisconnect(psPrivateData->ui32OpenPID);
                gui32ReleasePID = 0;
@@ -500,18 +858,56 @@ static int PVRSRVRelease(struct inode unref__ * pInode, struct file *pFile)
                                  psPrivateData, psPrivateData->hBlockAlloc);
 
 #if !defined(SUPPORT_DRI_DRM)
-               PRIVATE_DATA(pFile) = IMG_NULL; 
+               PRIVATE_DATA(pFile) = IMG_NULL; /*nulling shared pointer*/
 #endif
        }
 
+err_unlock:
        LinuxUnLockMutex(&gPVRSRVLock);
-
-#if !defined(SUPPORT_DRI_DRM)
-       return 0;
+#if defined(SUPPORT_DRI_DRM)
+       return;
+#else
+       return err;
 #endif
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             PVRCore_Init
+
+ @Description
+
+ Insert the driver into the kernel.
+
+ The device major number is allocated by the kernel dynamically.  This means
+ that the device node (nominally /dev/pvrsrv) will need to be re-made at boot
+ time if the number changes between subsequent loads of the module.  While the
+ number often stays constant between loads this is not guaranteed.  The node
+ is made as root on the shell with:
+
+               mknod /dev/pvrsrv c nnn 0
+
+ where nnn is the major number found in /proc/devices for DEVNAME and also
+ reported by the PVR_DPF() - look at the boot log using dmesg' to see this).
+
+ Currently the auto-generated script /etc/init.d/rc.pvr handles creation of
+ the device.  In other environments the device may be created either through
+ devfs or sysfs.
+
+ Readable proc-filesystem entries under /proc/pvr are created with
+ CreateProcEntries().  These can be read at runtime to get information about
+ the device (eg. 'cat /proc/pvr/vm')
+
+ __init places the function in a special memory section that the kernel frees
+ once the function has been run.  Refer also to module_init() macro call below.
+
+ @input none
+
+ @Return none
+
+*****************************************************************************/
 #if defined(SUPPORT_DRI_DRM)
 int PVRCore_Init(void)
 #else
@@ -521,16 +917,23 @@ static int __init PVRCore_Init(void)
        int error;
 #if !defined(PVR_LDM_MODULE)
        PVRSRV_ERROR eError;
-#else
+#endif
+#if !defined(SUPPORT_DRI_DRM) && defined(PVR_LDM_DEVICE_CLASS)
        struct device *psDev;
 #endif
 
 #if !defined(SUPPORT_DRI_DRM)
-       
+       /*
+        * Must come before attempting to print anything via Services.
+        * For DRM, the initialisation will already have been done.
+        */
        PVRDPFInit();
 #endif
        PVR_TRACE(("PVRCore_Init"));
 
+#if defined(PVR_LDM_MODULE) || defined(SUPPORT_DRI_DRM)
+       LinuxInitMutex(&gsPMMutex);
+#endif
        LinuxInitMutex(&gPVRSRVLock);
 
        if (CreateProcEntries ())
@@ -559,7 +962,7 @@ static int __init PVRCore_Init(void)
 
 #if defined(PVR_LDM_MODULE)
 
-#if defined(PVR_LDM_PLATFORM_MODULE)
+#if defined(PVR_LDM_PLATFORM_MODULE) || defined(SUPPORT_DRI_DRM_PLUGIN)
        if ((error = platform_driver_register(&powervr_driver)) != 0)
        {
                PVR_DPF((PVR_DBG_ERROR, "PVRCore_Init: unable to register platform driver (%d)", error));
@@ -577,7 +980,7 @@ static int __init PVRCore_Init(void)
                goto init_failed;
        }
 #endif
-#endif 
+#endif /* PVR_LDM_PLATFORM_MODULE */
 
 #if defined(PVR_LDM_PCI_MODULE)
        if ((error = pci_register_driver(&powervr_driver)) != 0)
@@ -586,10 +989,13 @@ static int __init PVRCore_Init(void)
 
                goto init_failed;
        }
-#endif 
+#endif /* PVR_LDM_PCI_MODULE */
+#endif /* defined(PVR_LDM_MODULE) */
 
-#else 
-       
+#if !defined(PVR_LDM_MODULE)
+       /*
+        * Drivers using LDM, will call SysInitialise in the probe/attach code
+        */
        if ((eError = SysInitialise()) != PVRSRV_OK)
        {
                error = -ENODEV;
@@ -602,7 +1008,7 @@ static int __init PVRCore_Init(void)
 #endif
                goto init_failed;
        }
-#endif 
+#endif /* !defined(PVR_LDM_MODULE) */
 
 #if !defined(SUPPORT_DRI_DRM)
        AssignedMajorNumber = register_chrdev(0, DEVNAME, &pvrsrv_fops);
@@ -616,10 +1022,12 @@ static int __init PVRCore_Init(void)
        }
 
        PVR_TRACE(("PVRCore_Init: major device %d", AssignedMajorNumber));
-#endif 
 
-#if defined(PVR_LDM_MODULE)
-       
+#if defined(PVR_LDM_DEVICE_CLASS)
+       /*
+        * This code (using GPL symbols) facilitates automatic device
+        * node creation on platforms with udev (or similar).
+        */
        psPvrClass = class_create(THIS_MODULE, "pvr");
 
        if (IS_ERR(psPvrClass))
@@ -632,7 +1040,7 @@ static int __init PVRCore_Init(void)
        psDev = device_create(psPvrClass, NULL, MKDEV(AssignedMajorNumber, 0),
 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26))
                                  NULL,
-#endif 
+#endif /* (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26)) */
                                  DEVNAME);
        if (IS_ERR(psDev))
        {
@@ -640,17 +1048,18 @@ static int __init PVRCore_Init(void)
                error = -EBUSY;
                goto destroy_class;
        }
-#endif 
+#endif /* defined(PVR_LDM_DEVICE_CLASS) */
+#endif /* !defined(SUPPORT_DRI_DRM) */
 
        return 0;
 
-#if defined(PVR_LDM_MODULE)
+#if !defined(SUPPORT_DRI_DRM)
+#if defined(PVR_LDM_DEVICE_CLASS)
 destroy_class:
        class_destroy(psPvrClass);
 unregister_device:
-       unregister_chrdev((IMG_UINT)AssignedMajorNumber, DRVNAME);
+       unregister_chrdev((IMG_UINT)AssignedMajorNumber, DEVNAME);
 #endif
-#if !defined(SUPPORT_DRI_DRM)
 sys_deinit:
 #endif
 #if defined(PVR_LDM_MODULE)
@@ -665,8 +1074,8 @@ sys_deinit:
        platform_driver_unregister(&powervr_driver);
 #endif
 
-#else  
-       
+#else  /* defined(PVR_LDM_MODULE) */
+       /* LDM drivers call SysDeinitialise during PVRSRVDriverRemove */
        {
                SYS_DATA *psSysData;
 
@@ -676,7 +1085,7 @@ sys_deinit:
                        (void) SysDeinitialise(psSysData);
                }
        }
-#endif 
+#endif /* defined(PVR_LDM_MODULE) */
 init_failed:
        PVRMMapCleanup();
        LinuxMMCleanup();
@@ -686,9 +1095,34 @@ init_failed:
 
        return error;
 
-} 
+} /*PVRCore_Init*/
+
+
+/*!
+*****************************************************************************
+
+ @Function             PVRCore_Cleanup
+
+ @Description  
+
+ Remove the driver from the kernel.
+
+ There's no way we can get out of being unloaded other than panicking; we
+ just do everything and plough on regardless of error.
+
+ __exit places the function in a special memory section that the kernel frees
+ once the function has been run.  Refer also to module_exit() macro call below.
 
+ Note that the for LDM on MontaVista kernels, the positioning of the driver
+ de-registration is the opposite way around than would be suggested by the
+ registration case or the 2,6 kernel case.  This is the correct way to do it
+ and the kernel panics if you change it.  You have been warned.
 
+ @input none
+
+ @Return none
+
+*****************************************************************************/
 #if defined(SUPPORT_DRI_DRM)
 void PVRCore_Cleanup(void)
 #else
@@ -704,25 +1138,26 @@ static void __exit PVRCore_Cleanup(void)
        SysAcquireData(&psSysData);
 #endif
 
-#if defined(PVR_LDM_MODULE)
+#if !defined(SUPPORT_DRI_DRM)
+
+#if defined(PVR_LDM_DEVICE_CLASS)
        device_destroy(psPvrClass, MKDEV(AssignedMajorNumber, 0));
        class_destroy(psPvrClass);
 #endif
 
-#if !defined(SUPPORT_DRI_DRM)
 #if (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22))
        if (
-#endif 
-               unregister_chrdev((IMG_UINT)AssignedMajorNumber, DRVNAME)
+#endif /* (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22)) */
+               unregister_chrdev((IMG_UINT)AssignedMajorNumber, DEVNAME)
 #if !(LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22))
                                                                ;
-#else  
+#else  /* (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22)) */
                                                                )
        {
                PVR_DPF((PVR_DBG_ERROR," can't unregister device major %d", AssignedMajorNumber));
        }
-#endif 
-#endif 
+#endif /* (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,22)) */
+#endif /* !defined(SUPPORT_DRI_DRM) */
 
 #if defined(PVR_LDM_MODULE)
 
@@ -737,7 +1172,7 @@ static void __exit PVRCore_Cleanup(void)
        platform_driver_unregister(&powervr_driver);
 #endif
 
-#else 
+#else /* defined(PVR_LDM_MODULE) */
 #if defined(DEBUG) && defined(PVR_MANUAL_POWER_CONTROL)
        if (gPVRPowerLevel != 0)
        {
@@ -747,9 +1182,9 @@ static void __exit PVRCore_Cleanup(void)
                }
        }
 #endif
-       
+       /* LDM drivers call SysDeinitialise during PVRSRVDriverRemove */
        (void) SysDeinitialise(psSysData);
-#endif 
+#endif /* defined(PVR_LDM_MODULE) */
 
        PVRMMapCleanup();
 
@@ -764,6 +1199,12 @@ static void __exit PVRCore_Cleanup(void)
        PVR_TRACE(("PVRCore_Cleanup: unloading"));
 }
 
+/*
+ * These macro calls define the initialisation and removal functions of the
+ * driver.  Although they are prefixed `module_', they apply when compiling
+ * statically as well; in both cases they define the function the kernel will
+ * run to start/stop the driver.
+*/
 #if !defined(SUPPORT_DRI_DRM)
 module_init(PVRCore_Init);
 module_exit(PVRCore_Cleanup);
index 742fa03..2cd666f 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux mutex interface
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 #include <linux/errno.h>
@@ -79,7 +94,7 @@ IMG_BOOL LinuxIsLockedMutex(PVRSRV_LINUX_MUTEX *psPVRSRVMutex)
 }
 
 
-#else 
+#else /* (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,15)) */
 
 
 IMG_VOID LinuxInitMutex(PVRSRV_LINUX_MUTEX *psPVRSRVMutex)
@@ -98,7 +113,9 @@ PVRSRV_ERROR LinuxLockMutexInterruptible(PVRSRV_LINUX_MUTEX *psPVRSRVMutex)
 {
     if(down_interruptible(&psPVRSRVMutex->sSemaphore) == -EINTR)
     {
-        
+        /* The process was sent a signal while waiting for the semaphore
+         * (e.g. a kill signal from userspace)
+         */
         return PVRSRV_ERROR_MUTEX_INTERRUPTIBLE_ERROR;
     }else{
         atomic_dec(&psPVRSRVMutex->Count);
@@ -132,5 +149,5 @@ IMG_BOOL LinuxIsLockedMutex(PVRSRV_LINUX_MUTEX *psPVRSRVMutex)
     return (IMG_BOOL)iCount;
 }
 
-#endif 
+#endif /* (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,15)) */
 
index 5e787b7..c590da1 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux mutex interface
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
 
 #ifndef __INCLUDED_LINUX_MUTEX_H_
 #define __INCLUDED_LINUX_MUTEX_H_
 
 typedef struct mutex PVRSRV_LINUX_MUTEX;
 
-#else 
+#else /* (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,15)) */
 
 
 typedef struct {
     struct semaphore sSemaphore;
-    
+    /* since Linux's struct semaphore is intended to be
+     * opaque we don't poke inside for the count and
+     * instead we track it outselves. (So we can implement
+     * LinuxIsLockedMutex)
+     */
     atomic_t Count;
 }PVRSRV_LINUX_MUTEX;
 
@@ -66,5 +86,5 @@ extern IMG_VOID LinuxUnLockMutex(PVRSRV_LINUX_MUTEX *psPVRSRVMutex);
 extern IMG_BOOL LinuxIsLockedMutex(PVRSRV_LINUX_MUTEX *psPVRSRVMutex);
 
 
-#endif 
+#endif /* __INCLUDED_LINUX_MUTEX_H_ */
 
index a012cf5..8e57476 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux memory interface support functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 
@@ -77,15 +92,23 @@ pvr_pat_entry(u64 pat, IMG_UINT index)
 static IMG_VOID
 PVRLinuxX86PATProbe(IMG_VOID)
 {
-       
-       if (cpu_has_pat)         
+       /*
+        * cpu_has_pat indicates whether PAT support is available on the CPU,
+        * but doesn't indicate if it has been enabled.
+        */
+       if (cpu_has_pat)        /* PRQA S 3335 */ /* ignore 'no function declared' */
        {
                u64 pat;
                IMG_UINT pat_index;
                IMG_UINT pat_entry;
 
                PVR_TRACE(("%s: PAT available", __FUNCTION__));
-               
+               /*
+                * There is no Linux API for finding out if write combining
+                * is avaialable through the PAT, so we take the direct
+                * approach, and see if the PAT MSR contains a write combining
+                * entry.
+                */
                rdmsrl(MSR_IA32_CR_PAT, pat);
                PVR_TRACE(("%s: Top 32 bits of PAT: 0x%.8x", __FUNCTION__, (IMG_UINT)(pat >> 32)));
                PVR_TRACE(("%s: Bottom 32 bits of PAT: 0x%.8x", __FUNCTION__, (IMG_UINT)(pat)));
@@ -110,21 +133,28 @@ PVRLinuxX86PATProbe(IMG_VOID)
        {
                PVR_TRACE(("%s: Write combining not available", __FUNCTION__));
        }
-#else  
+#else  /* defined(SUPPORT_LINUX_X86_WRITECOMBINE) */
        PVR_TRACE(("%s: Write combining disabled in driver build", __FUNCTION__));
-#endif 
-#endif 
+#endif /* defined(SUPPORT_LINUX_X86_WRITECOMBINE) */
+#endif /* DEBUG */
 }
 
 pgprot_t
 pvr_pgprot_writecombine(pgprot_t prot)
 {
-    
-     
+    /*
+     * It would be worth checking from time to time to see if a
+     * pgprot_writecombine function (or similar) is introduced on Linux for
+     * x86 processors.  If so, this function, and PVRLinuxX86PATProbe can be
+     * removed, and a macro used to select between pgprot_writecombine and
+     * pgprot_noncached, dpending on the value for of
+     * SUPPORT_LINUX_X86_WRITECOMBINE.
+     */
+    /* PRQA S 0481,0482 2 */ /* scalar expressions */
     return (g_write_combining_available) ?
                __pgprot((pgprot_val(prot) & ~_PAGE_CACHE_MASK) | _PAGE_CACHE_WC) : pgprot_noncached(prot);
 }
-#endif 
+#endif /* defined(SUPPORT_LINUX_X86_PAT) */
 
 IMG_VOID
 PVRLinuxMUtilsInit(IMG_VOID)
index b2a8ba0..891598c 100644 (file)
@@ -1,29 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Memory management support utils
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Declares various memory management support functions
+                for Linux.
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __IMG_LINUX_MUTILS_H__
 #define __IMG_LINUX_MUTILS_H__
 
 
 IMG_VOID PVRLinuxMUtilsInit(IMG_VOID);
 
-#endif 
+#endif /* __IMG_LINUX_MUTILS_H__ */
 
index ff92a63..33658c1 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Environment related functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 
 #include "event.h"
 #include "linkage.h"
 #include "pvr_uaccess.h"
+#include "lock.h"
+
+#if defined (SUPPORT_ION)
+#include "ion.h"
+#endif
+
+#if defined (CONFIG_X86_PAE)
+#error Physical Address Extension not supported with the driver
+#endif
 
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,27))
 #define ON_EACH_CPU(func, info, wait) on_each_cpu(func, info, wait)
 #define ON_EACH_CPU(func, info, wait) on_each_cpu(func, info, 0, wait)
 #endif
 
-//#if defined(PVR_LINUX_USING_WORKQUEUES) && !defined(CONFIG_PREEMPT)
+#if defined(PVR_LINUX_USING_WORKQUEUES) && !defined(CONFIG_PREEMPT)
+/* 
+ * Services spins at certain points waiting for events (e.g. swap
+ * chain destrucion).  If those events rely on workqueues running,
+ * it needs to be possible to preempt the waiting thread.
+ * Removing the need for CONFIG_PREEMPT will require adding preemption
+ * points at various points in Services.
+ */
 //#error "A preemptible Linux kernel is required when using workqueues"
-//#endif
+#endif
 
 #if defined(EMULATOR)
 #define EVENT_OBJECT_TIMEOUT_MS                (2000)
 #else
 #define EVENT_OBJECT_TIMEOUT_MS                (100)
-#endif 
+#endif /* EMULATOR */
 
 #if !defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 PVRSRV_ERROR OSAllocMem_Impl(IMG_UINT32 ui32Flags, IMG_UINT32 ui32Size, IMG_PVOID *ppvCpuVAddr, IMG_HANDLE *phBlockAlloc)
@@ -101,7 +132,7 @@ PVRSRV_ERROR OSAllocMem_Impl(IMG_UINT32 ui32Flags, IMG_UINT32 ui32Size, IMG_PVOI
 
     if (ui32Size > PAGE_SIZE)
     {
-        
+        /* Try to allocate the memory using vmalloc */
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
         *ppvCpuVAddr = _VMallocWrapper(ui32Size, PVRSRV_HAP_CACHED, pszFilename, ui32Line);
 #else
@@ -134,7 +165,7 @@ static inline int is_vmalloc_addr(const void *pvCpuVAddr)
        return lAddr >= VMALLOC_START && lAddr < VMALLOC_END;
 }
 
-#endif 
+#endif /* (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,24)) */
 
 #if !defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
 PVRSRV_ERROR OSFreeMem_Impl(IMG_UINT32 ui32Flags, IMG_UINT32 ui32Size, IMG_PVOID pvCpuVAddr, IMG_HANDLE hBlockAlloc)
@@ -171,6 +202,9 @@ PVRSRV_ERROR
 OSAllocPages_Impl(IMG_UINT32 ui32AllocFlags,
                                  IMG_UINT32 ui32Size,
                                  IMG_UINT32 ui32PageSize,
+                                 IMG_PVOID pvPrivData,
+                                 IMG_UINT32 ui32PrivDataLength,
+                                 IMG_HANDLE hBMHandle,
                                  IMG_VOID **ppvCpuVAddr,
                                  IMG_HANDLE *phOSMemHandle)
 {
@@ -179,7 +213,8 @@ OSAllocPages_Impl(IMG_UINT32 ui32AllocFlags,
     PVR_UNREFERENCED_PARAMETER(ui32PageSize);
 
 #if 0
-    
+    /* For debug: force all OSAllocPages allocations to have a kernel
+     * virtual address */
     if(ui32AllocFlags & PVRSRV_HAP_SINGLE_PROCESS)
     {
         ui32AllocFlags &= ~PVRSRV_HAP_SINGLE_PROCESS;
@@ -187,6 +222,22 @@ OSAllocPages_Impl(IMG_UINT32 ui32AllocFlags,
     }
 #endif
 
+    if(ui32AllocFlags & PVRSRV_MEM_ION)
+    {
+        /* We'll only see HAP_SINGLE_PROCESS with MEM_ION */
+        BUG_ON((ui32AllocFlags & PVRSRV_HAP_MAPTYPE_MASK) != PVRSRV_HAP_SINGLE_PROCESS);
+
+        psLinuxMemArea = NewIONLinuxMemArea(ui32Size, ui32AllocFlags,
+                                                                                       pvPrivData, ui32PrivDataLength);
+        if(!psLinuxMemArea)
+        {
+            return PVRSRV_ERROR_OUT_OF_MEMORY;
+        }
+
+        PVRMMapRegisterArea(psLinuxMemArea);
+        goto ExitSkipSwitch;
+    }
+
     switch(ui32AllocFlags & PVRSRV_HAP_MAPTYPE_MASK)
     {
         case PVRSRV_HAP_KERNEL_ONLY:
@@ -200,8 +251,9 @@ OSAllocPages_Impl(IMG_UINT32 ui32AllocFlags,
         }
         case PVRSRV_HAP_SINGLE_PROCESS:
         {
-            
-            
+            /* Currently PVRSRV_HAP_SINGLE_PROCESS implies that we dont need a
+             * kernel virtual mapping, but will need a user space virtual mapping */
+
             psLinuxMemArea = NewAllocPagesLinuxMemArea(ui32Size, ui32AllocFlags);
             if(!psLinuxMemArea)
             {
@@ -213,9 +265,17 @@ OSAllocPages_Impl(IMG_UINT32 ui32AllocFlags,
 
         case PVRSRV_HAP_MULTI_PROCESS:
         {
-            
+            /* Currently PVRSRV_HAP_MULTI_PROCESS implies that we need a kernel
+             * virtual mapping and potentially multiple user space virtual
+             * mappings: Note: these eat into our limited kernel virtual
+             * address space. */
+
 #if defined(VIVT_CACHE) || defined(__sh__)
-            
+            /* ARM9 caches are tagged with virtual pages, not physical. As we are going to
+             * share this memory in different address spaces, we don't want it to be cached.
+             * ARM11 has physical tagging, so we can cache this memory without fear of virtual
+             * address aliasing in the TLB, as long as the kernel supports cache colouring for
+             * VIPT architectures. */
             ui32AllocFlags &= ~PVRSRV_HAP_CACHED;
 #endif
             psLinuxMemArea = NewVMallocLinuxMemArea(ui32Size, ui32AllocFlags);
@@ -233,6 +293,16 @@ OSAllocPages_Impl(IMG_UINT32 ui32AllocFlags,
             return PVRSRV_ERROR_INVALID_PARAMS;
     }
 
+       /*
+               In case of sparse mapping we need to handle back to the BM as it
+               knows the mapping info
+       */
+       if (ui32AllocFlags & PVRSRV_MEM_SPARSE)
+       {
+               psLinuxMemArea->hBMHandle = hBMHandle;
+       }
+
+ExitSkipSwitch:
     *ppvCpuVAddr = LinuxMemAreaToCpuVAddr(psLinuxMemArea);
     *phOSMemHandle = psLinuxMemArea;
     
@@ -301,7 +371,7 @@ OSGetSubMemHandle(IMG_HANDLE hOSMemHandle,
     }
     *phOSMemHandleRet = psLinuxMemArea;
 
-    
+    /* KERNEL_ONLY areas are never mmapable. */
     if(ui32Flags & PVRSRV_HAP_KERNEL_ONLY)
     {
         return PVRSRV_OK;
@@ -353,7 +423,33 @@ OSMemHandleToCpuPAddr(IMG_VOID *hOSMemHandle, IMG_UINT32 ui32ByteOffset)
 }
 
 
+IMG_BOOL OSMemHandleIsPhysContig(IMG_VOID *hOSMemHandle)
+{
+       LinuxMemArea *psLinuxMemArea = (LinuxMemArea *)hOSMemHandle;
+
+       PVR_ASSERT(psLinuxMemArea);
+
+       if(psLinuxMemArea->eAreaType == LINUX_MEM_AREA_EXTERNAL_KV)
+               return psLinuxMemArea->uData.sExternalKV.bPhysContig;
+
+       return IMG_FALSE;
+}
+
+
+/*!
+******************************************************************************
+
+ @Function             OSMemCopy
+
+ @Description  Copies memory around
 
+ @Input    pvDst - pointer to dst
+ @Output   pvSrc - pointer to src
+ @Input    ui32Size - bytes to copy
+
+ @Return  none
+
+******************************************************************************/
 IMG_VOID OSMemCopy(IMG_VOID *pvDst, IMG_VOID *pvSrc, IMG_UINT32 ui32Size)
 {
 #if defined(USE_UNOPTIMISED_MEMCPY)
@@ -372,6 +468,22 @@ IMG_VOID OSMemCopy(IMG_VOID *pvDst, IMG_VOID *pvSrc, IMG_UINT32 ui32Size)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     OSMemSet
+
+ @Description Function that does the same as the C memset() functions
+
+ @Modified *pvDest :   pointer to start of buffer to be set
+
+ @Input    ui8Value:   value to set each byte to
+
+ @Input    ui32Size :  number of bytes to set
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 IMG_VOID OSMemSet(IMG_VOID *pvDest, IMG_UINT8 ui8Value, IMG_UINT32 ui32Size)
 {
 #if defined(USE_UNOPTIMISED_MEMSET)
@@ -389,11 +501,21 @@ IMG_VOID OSMemSet(IMG_VOID *pvDest, IMG_UINT8 ui8Value, IMG_UINT32 ui32Size)
 }
 
 
+/*!
+******************************************************************************
+ @Function     OSStringCopy
+ @Description strcpy
+******************************************************************************/
 IMG_CHAR *OSStringCopy(IMG_CHAR *pszDest, const IMG_CHAR *pszSrc)
 {
     return (strcpy(pszDest, pszSrc));
 }
 
+/*!
+******************************************************************************
+ @Function     OSSNPrintf
+ @Description snprintf
+******************************************************************************/
 IMG_INT32 OSSNPrintf(IMG_CHAR *pStr, IMG_UINT32 ui32Size, const IMG_CHAR *pszFormat, ...)
 {
     va_list argList;
@@ -406,6 +528,19 @@ IMG_INT32 OSSNPrintf(IMG_CHAR *pStr, IMG_UINT32 ui32Size, const IMG_CHAR *pszFor
     return iCount;
 }
 
+/*!
+******************************************************************************
+
+ @Function OSBreakResourceLock
+
+ @Description unlocks an OS dependant resource
+
+ @Input phResource - pointer to OS dependent resource structure
+ @Input ui32ID - Lock value to look for
+
+ @Return
+
+******************************************************************************/
 IMG_VOID OSBreakResourceLock (PVRSRV_RESOURCE *psResource, IMG_UINT32 ui32ID)
 {
     volatile IMG_UINT32 *pui32Access = (volatile IMG_UINT32 *)&psResource->ui32Lock;
@@ -429,6 +564,18 @@ IMG_VOID OSBreakResourceLock (PVRSRV_RESOURCE *psResource, IMG_UINT32 ui32ID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function OSCreateResource
+
+ @Description creates a OS dependant resource object
+
+ @Input phResource - pointer to OS dependent resource
+
+ @Return error status
+
+******************************************************************************/
 PVRSRV_ERROR OSCreateResource(PVRSRV_RESOURCE *psResource)
 {
     psResource->ui32ID = 0;
@@ -438,6 +585,18 @@ PVRSRV_ERROR OSCreateResource(PVRSRV_RESOURCE *psResource)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function OSDestroyResource
+
+ @Description destroys an OS dependant resource object
+
+ @Input phResource - pointer to OS dependent resource
+
+ @Return error status
+
+******************************************************************************/
 PVRSRV_ERROR OSDestroyResource (PVRSRV_RESOURCE *psResource)
 {
     OSBreakResourceLock (psResource, psResource->ui32ID);
@@ -446,12 +605,26 @@ PVRSRV_ERROR OSDestroyResource (PVRSRV_RESOURCE *psResource)
 }
 
 
+/*!
+******************************************************************************
+
+  @Function            OSInitEnvData
+
+  @Description Allocates space for env specific data
+
+  @Input               ppvEnvSpecificData - pointer to pointer in which to return
+                allocated data.
+  @Input               ui32MMUMode - MMU mode.
+
+  @Return              nothing
+
+******************************************************************************/
 PVRSRV_ERROR OSInitEnvData(IMG_PVOID *ppvEnvSpecificData)
 {
     ENV_DATA           *psEnvData;
     PVRSRV_ERROR       eError;
     
-    
+    /* allocate env specific data */
     eError = OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(ENV_DATA), (IMG_VOID **)&psEnvData, IMG_NULL,
         "Environment Data");
     if (eError != PVRSRV_OK)
@@ -465,22 +638,34 @@ PVRSRV_ERROR OSInitEnvData(IMG_PVOID *ppvEnvSpecificData)
     if (eError != PVRSRV_OK)
     {
         OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(ENV_DATA), psEnvData, IMG_NULL);
-               
+               /*not nulling pointer, out of scope*/
         return eError;
     }
 
 
-    
+    /* ISR installation flags */
     psEnvData->bMISRInstalled = IMG_FALSE;
     psEnvData->bLISRInstalled = IMG_FALSE;
 
-    
+    /* copy structure back */
     *ppvEnvSpecificData = psEnvData;
 
     return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSDeInitEnvData
+
+ @Description  frees env specific data memory
+
+ @Input    pvEnvSpecificData - pointer to private structure
+
+ @Return   PVRSRV_OK on success else PVRSRV_ERROR_OUT_OF_MEMORY
+
+******************************************************************************/
 PVRSRV_ERROR OSDeInitEnvData(IMG_PVOID pvEnvSpecificData)
 {
     ENV_DATA           *psEnvData = (ENV_DATA*)pvEnvSpecificData;
@@ -492,20 +677,42 @@ PVRSRV_ERROR OSDeInitEnvData(IMG_PVOID pvEnvSpecificData)
     psEnvData->pvBridgeData = IMG_NULL;
 
     OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(ENV_DATA), pvEnvSpecificData, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
     return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function OSReleaseThreadQuanta
  
+ @Description
+    Releases thread quanta
+     
+ @Return nothing
+
+******************************************************************************/ 
 IMG_VOID OSReleaseThreadQuanta(IMG_VOID)
 {
     schedule();
 }
 
 
+/*!
+******************************************************************************
+
+ @Function OSClockus
+ @Description 
+    This function returns the clock in microseconds
  
+ @Input void
+
+ @Return - clock (us)
+
+******************************************************************************/ 
 IMG_UINT32 OSClockus(IMG_VOID)
 {
     IMG_UINT32 time, j = jiffies;
@@ -528,25 +735,71 @@ IMG_VOID OSSleepms(IMG_UINT32 ui32Timems)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function OSFuncHighResTimerCreate
+ @Description 
+    This function creates a high res timer who's handle is returned
  
+ @Input nothing
+
+ @Return handle
+
+******************************************************************************/ 
 IMG_HANDLE OSFuncHighResTimerCreate(IMG_VOID)
 {
-       
+       /* We don't need a handle, but we must return non-NULL */
        return (IMG_HANDLE) 1;
 }
 
+/*!
+******************************************************************************
+
+ @Function OSFuncHighResTimerGetus
  
+ @Description 
+    This function returns the current timestamp in us
+ @Input nothing
+
+ @Return handle
+
+******************************************************************************/ 
 IMG_UINT32 OSFuncHighResTimerGetus(IMG_HANDLE hTimer)
 {
        return (IMG_UINT32) jiffies_to_usecs(jiffies);
 }
 
+/*!
+******************************************************************************
+
+ @Function OSFuncHighResTimerDestroy
  
+ @Description 
+    This function will destroy the high res timer
+ @Input nothing
+
+ @Return handle
+
+******************************************************************************/ 
 IMG_VOID OSFuncHighResTimerDestroy(IMG_HANDLE hTimer)
 {
        PVR_UNREFERENCED_PARAMETER(hTimer);
 }
 
+/*!
+******************************************************************************
+
+  @Function            OSGetCurrentProcessIDKM
+
+  @Description Returns handle for current process
+
+  @Return    ID of current process
+
+*****************************************************************************/
 IMG_UINT32 OSGetCurrentProcessIDKM(IMG_VOID)
 {
     if (in_interrupt())
@@ -566,6 +819,16 @@ IMG_UINT32 OSGetCurrentProcessIDKM(IMG_VOID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSGetPageSize
+ @Description  gets page size
+    
+ @Return               page size
+
+******************************************************************************/
 IMG_UINT32 OSGetPageSize(IMG_VOID)
 {
 #if defined(__sh__)
@@ -578,6 +841,16 @@ IMG_UINT32 OSGetPageSize(IMG_VOID)
 }
 
 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0))
+/*!
+******************************************************************************
+
+ @Function             DeviceISRWrapper
+ @Description  wrapper for Device ISR function to conform to ISR OS interface
+    
+ @Return
+
+******************************************************************************/
 static irqreturn_t DeviceISRWrapper(int irq, void *dev_id
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,19))
         , struct pt_regs *regs
@@ -614,6 +887,19 @@ out:
 
 
 
+/*!
+******************************************************************************
+
+ @Function             SystemISRWrapper
+ @Description  wrapper for System ISR function to conform to ISR OS interface
+
+ @Input    Interrupt - NT interrupt object.
+ @Input    Context - Context parameter 
+    
+ @Return
+
+******************************************************************************/
 static irqreturn_t SystemISRWrapper(int irq, void *dev_id
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,19))
         , struct pt_regs *regs
@@ -647,6 +933,21 @@ out:
     return bStatus ? IRQ_HANDLED : IRQ_NONE;
 #endif
 }
+/*!
+******************************************************************************
+
+ @Function             OSInstallDeviceLISR
+ @Description  Installs a Device ISR
+    
+ @Input    pvSysData
+ @Input    ui32Irq - IRQ number
+ @Input    pszISRName - ISR name
+ @Input    pvDeviceNode - device node contains ISR function and data argument
+
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSInstallDeviceLISR(IMG_VOID *pvSysData,
                                     IMG_UINT32 ui32Irq,
                                     IMG_CHAR *pszISRName,
@@ -683,6 +984,18 @@ PVRSRV_ERROR OSInstallDeviceLISR(IMG_VOID *pvSysData,
     return PVRSRV_OK;  
 }
 
+/*!
+******************************************************************************
+
+ @Function             OSUninstallDeviceLISR
+ @Description  Uninstalls a Device ISR
+    
+ @Input    pvSysData - sysdata
+
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSUninstallDeviceLISR(IMG_VOID *pvSysData)
 {
     SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -704,6 +1017,19 @@ PVRSRV_ERROR OSUninstallDeviceLISR(IMG_VOID *pvSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSInstallSystemLISR
+ @Description  Installs a System ISR
+    
+ @Input    psSysData
+ @Input    ui32Irq - IRQ number
+
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSInstallSystemLISR(IMG_VOID *pvSysData, IMG_UINT32 ui32Irq)
 {
     SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -738,6 +1064,18 @@ PVRSRV_ERROR OSInstallSystemLISR(IMG_VOID *pvSysData, IMG_UINT32 ui32Irq)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSUninstallSystemLISR
+ @Description  Uninstalls a System ISR
+    
+ @Input    psSysData
+
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSUninstallSystemLISR(IMG_VOID *pvSysData)
 {
     SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -759,6 +1097,18 @@ PVRSRV_ERROR OSUninstallSystemLISR(IMG_VOID *pvSysData)
 }
 
 #if defined(PVR_LINUX_MISR_USING_PRIVATE_WORKQUEUE)
+/*!
+******************************************************************************
+
+ @Function             MISRWrapper
+ @Description  OS dependent MISR wrapper
+       
+ @Input    psSysData
+
+ @Return   error status 
+
+******************************************************************************/
 static void MISRWrapper(
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,20))
                        void *data
@@ -774,6 +1124,18 @@ static void MISRWrapper(
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSInstallMISR
+ @Description  Installs an OS dependent MISR
+
+ @Input    psSysData
+       
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSInstallMISR(IMG_VOID *pvSysData)
 {
        SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -808,6 +1170,18 @@ PVRSRV_ERROR OSInstallMISR(IMG_VOID *pvSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSUninstallMISR
+ @Description  Uninstalls an OS dependent MISR
+
+ @Input    psSysData
+       
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSUninstallMISR(IMG_VOID *pvSysData)
 {
        SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -829,6 +1203,18 @@ PVRSRV_ERROR OSUninstallMISR(IMG_VOID *pvSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSScheduleMISR
+ @Description  Schedules an OS dependent MISR
+
+ @Input    pvSysData
+       
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSScheduleMISR(IMG_VOID *pvSysData)
 {
        SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -841,8 +1227,20 @@ PVRSRV_ERROR OSScheduleMISR(IMG_VOID *pvSysData)
 
        return PVRSRV_OK;       
 }
-#else  
+#else  /* defined(PVR_LINUX_MISR_USING_PRIVATE_WORKQUEUE) */
 #if defined(PVR_LINUX_MISR_USING_WORKQUEUE)
+/*!
+******************************************************************************
+
+ @Function             MISRWrapper
+ @Description  OS dependent MISR wrapper
+       
+ @Input    psSysData
+
+ @Return   error status 
+
+******************************************************************************/
 static void MISRWrapper(
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,20))
                        void *data
@@ -858,6 +1256,18 @@ static void MISRWrapper(
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSInstallMISR
+ @Description  Installs an OS dependent MISR
+
+ @Input    psSysData
+       
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSInstallMISR(IMG_VOID *pvSysData)
 {
        SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -884,6 +1294,18 @@ PVRSRV_ERROR OSInstallMISR(IMG_VOID *pvSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSUninstallMISR
+ @Description  Uninstalls an OS dependent MISR
+
+ @Input    psSysData
+       
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSUninstallMISR(IMG_VOID *pvSysData)
 {
        SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -905,6 +1327,18 @@ PVRSRV_ERROR OSUninstallMISR(IMG_VOID *pvSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSScheduleMISR
+ @Description  Schedules an OS dependent MISR
+
+ @Input    pvSysData
+       
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSScheduleMISR(IMG_VOID *pvSysData)
 {
        SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -918,9 +1352,21 @@ PVRSRV_ERROR OSScheduleMISR(IMG_VOID *pvSysData)
        return PVRSRV_OK;       
 }
 
-#else  
+#else  /* #if defined(PVR_LINUX_MISR_USING_WORKQUEUE) */
 
 
+/*!
+******************************************************************************
+
+ @Function             MISRWrapper
+ @Description  OS dependent MISR wrapper
+    
+ @Input    psSysData
+
+ @Return   error status 
+
+******************************************************************************/
 static void MISRWrapper(unsigned long data)
 {
     SYS_DATA *psSysData;
@@ -931,6 +1377,18 @@ static void MISRWrapper(unsigned long data)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSInstallMISR
+ @Description  Installs an OS dependent MISR
+
+ @Input    psSysData
+    
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSInstallMISR(IMG_VOID *pvSysData)
 {
     SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -952,6 +1410,18 @@ PVRSRV_ERROR OSInstallMISR(IMG_VOID *pvSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSUninstallMISR
+ @Description  Uninstalls an OS dependent MISR
+
+ @Input    psSysData
+    
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSUninstallMISR(IMG_VOID *pvSysData)
 {
     SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -972,6 +1442,18 @@ PVRSRV_ERROR OSUninstallMISR(IMG_VOID *pvSysData)
     return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function             OSScheduleMISR
+ @Description  Schedules an OS dependent MISR
+
+ @Input    pvSysData
+    
+ @Return   error status 
+
+******************************************************************************/
 PVRSRV_ERROR OSScheduleMISR(IMG_VOID *pvSysData)
 {
     SYS_DATA *psSysData = (SYS_DATA*)pvSysData;
@@ -985,10 +1467,10 @@ PVRSRV_ERROR OSScheduleMISR(IMG_VOID *pvSysData)
     return PVRSRV_OK;  
 }
 
-#endif 
-#endif 
+#endif /* #if defined(PVR_LINUX_MISR_USING_WORKQUEUE) */
+#endif /* #if defined(PVR_LINUX_MISR_USING_PRIVATE_WORKQUEUE) */
 
-#endif 
+#endif /* #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,20)) */
 
 IMG_VOID OSPanic(IMG_VOID)
 {
@@ -1000,6 +1482,19 @@ IMG_VOID OSPanic(IMG_VOID)
 #else
 #define        OS_TAS(p)       tas(p)
 #endif
+/*!
+******************************************************************************
+
+ @Function OSLockResource
+
+ @Description locks an OS dependant Resource
+
+ @Input phResource - pointer to OS dependent Resource
+ @Input bBlock - do we want to block?
+
+ @Return error status
+
+******************************************************************************/
 PVRSRV_ERROR OSLockResource ( PVRSRV_RESOURCE  *psResource,
                                 IMG_UINT32                     ui32ID)
 
@@ -1015,6 +1510,18 @@ PVRSRV_ERROR OSLockResource ( PVRSRV_RESOURCE    *psResource,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function OSUnlockResource
+
+ @Description unlocks an OS dependant resource
+
+ @Input phResource - pointer to OS dependent resource structure
+
+ @Return
+
+******************************************************************************/
 PVRSRV_ERROR OSUnlockResource (PVRSRV_RESOURCE *psResource, IMG_UINT32 ui32ID)
 {
     volatile IMG_UINT32 *pui32Access = (volatile IMG_UINT32 *)&psResource->ui32Lock;
@@ -1045,6 +1552,18 @@ PVRSRV_ERROR OSUnlockResource (PVRSRV_RESOURCE *psResource, IMG_UINT32 ui32ID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function OSIsResourceLocked
+
+ @Description tests if resource is locked
+
+ @Input phResource - pointer to OS dependent resource structure
+
+ @Return error status
+
+******************************************************************************/
 IMG_BOOL OSIsResourceLocked (PVRSRV_RESOURCE *psResource, IMG_UINT32 ui32ID)
 {
     volatile IMG_UINT32 *pui32Access = (volatile IMG_UINT32 *)&psResource->ui32Lock;
@@ -1066,7 +1585,7 @@ PVRSRV_ERROR OSPowerLockWrap(IMG_BOOL bTryLock)
 IMG_VOID OSPowerLockUnwrap (IMG_VOID)
 {
 }
-#endif 
+#endif /* SYS_CUSTOM_POWERLOCK_WRAP */
 
 
 IMG_CPU_PHYADDR OSMapLinToCPUPhys(IMG_HANDLE hOSMemHandle,
@@ -1079,8 +1598,6 @@ IMG_CPU_PHYADDR OSMapLinToCPUPhys(IMG_HANDLE hOSMemHandle,
 
        PVR_ASSERT(hOSMemHandle != IMG_NULL);
 
-       
-
        psLinuxMemArea = (LinuxMemArea *)hOSMemHandle;
 
        uiByteOffset = (IMG_UINTPTR_T)pvLinAddr - (IMG_UINTPTR_T)LinuxMemAreaToCpuVAddr(psLinuxMemArea);
@@ -1092,6 +1609,22 @@ IMG_CPU_PHYADDR OSMapLinToCPUPhys(IMG_HANDLE hOSMemHandle,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             OSMapPhysToLin
+
+ @Description  Maps the physical memory into linear addr range
+
+ @Input    BasePAddr : physical cpu address
+
+ @Input    ui32Bytes - bytes to map
+
+ @Input    ui32CacheType - cache type
+
+ @Return    : Linear addr of mapping on success, else NULL
+
+ ******************************************************************************/
 IMG_VOID *
 OSMapPhysToLin(IMG_CPU_PHYADDR BasePAddr,
                IMG_UINT32 ui32Bytes,
@@ -1100,7 +1633,11 @@ OSMapPhysToLin(IMG_CPU_PHYADDR BasePAddr,
 {
     if(ui32MappingFlags & PVRSRV_HAP_KERNEL_ONLY)
     {
-       
+       /* 
+        * Provide some backwards compatibility, until all callers
+        * have been updated to pass a non-null OSMemHandle pointer.
+        * Such callers must not call OSMapLinToCPUPhys.
+        */
        if(phOSMemHandle == IMG_NULL)
        {
                IMG_VOID *pvIORemapCookie;
@@ -1132,11 +1669,15 @@ OSMapPhysToLin(IMG_CPU_PHYADDR BasePAddr,
     return IMG_NULL;
 }
 
+/*!
+******************************************************************************
+ @Function     OSUnMapPhysToLin
+ @Description Unmaps memory that was mapped with OSMapPhysToLin
+ @Return TRUE on success, else FALSE
+******************************************************************************/
 IMG_BOOL
 OSUnMapPhysToLin(IMG_VOID *pvLinAddr, IMG_UINT32 ui32Bytes, IMG_UINT32 ui32MappingFlags, IMG_HANDLE hOSMemHandle)
 {
-    PVR_TRACE(("%s: unmapping %d bytes from %p", __FUNCTION__, ui32Bytes, pvLinAddr));
-
     PVR_UNREFERENCED_PARAMETER(ui32Bytes);     
 
     if(ui32MappingFlags & PVRSRV_HAP_KERNEL_ONLY)
@@ -1163,6 +1704,12 @@ OSUnMapPhysToLin(IMG_VOID *pvLinAddr, IMG_UINT32 ui32Bytes, IMG_UINT32 ui32Mappi
     return IMG_FALSE;
 }
 
+/*!
+******************************************************************************
+ @Function     RegisterExternalMem
+ @Description Registers external memory for user mode mapping
+ @Return TRUE on success, else FALSE, MemHandle out
+******************************************************************************/
 static PVRSRV_ERROR
 RegisterExternalMem(IMG_SYS_PHYADDR *pBasePAddr,
           IMG_VOID *pvCPUVAddr,
@@ -1198,9 +1745,18 @@ RegisterExternalMem(IMG_SYS_PHYADDR *pBasePAddr,
         }
         case PVRSRV_HAP_MULTI_PROCESS:
         {
-            
+            /* Currently PVRSRV_HAP_MULTI_PROCESS implies that we need a kernel
+             * virtual mapping and potentially multiple user space virtual mappings.
+             * Beware that the kernel virtual address space is a limited resource.
+             */
 #if defined(VIVT_CACHE) || defined(__sh__)
-            
+            /* 
+             * ARM9 caches are tagged with virtual pages, not physical. As we are going to
+             * share this memory in different address spaces, we don't want it to be cached.
+             * ARM11 has physical tagging, so we can cache this memory without fear of virtual
+             * address aliasing in the TLB, as long as the kernel supports cache colouring for
+             * VIPT architectures.
+             */
             ui32MappingFlags &= ~PVRSRV_HAP_CACHED;
 #endif
         psLinuxMemArea = NewExternalKVLinuxMemArea(pBasePAddr, pvCPUVAddr, ui32Bytes, bPhysContig, ui32MappingFlags);
@@ -1226,6 +1782,13 @@ RegisterExternalMem(IMG_SYS_PHYADDR *pBasePAddr,
 }
 
 
+/*!
+******************************************************************************
+ @Function     OSRegisterMem
+ @Description Registers external memory for user mode mapping
+ @Output phOSMemHandle - handle to registered memory
+ @Return TRUE on success, else FALSE
+******************************************************************************/
 PVRSRV_ERROR
 OSRegisterMem(IMG_CPU_PHYADDR BasePAddr,
               IMG_VOID *pvCPUVAddr,
@@ -1245,6 +1808,12 @@ PVRSRV_ERROR OSRegisterDiscontigMem(IMG_SYS_PHYADDR *pBasePAddr, IMG_VOID *pvCPU
 }
 
 
+/*!
+******************************************************************************
+ @Function     OSUnRegisterMem
+ @Description UnRegisters external memory for user mode mapping
+ @Return TRUE on success, else FALSE
+******************************************************************************/
 PVRSRV_ERROR
 OSUnRegisterMem (IMG_VOID *pvCpuVAddr,
                 IMG_UINT32 ui32Bytes,
@@ -1291,17 +1860,27 @@ PVRSRV_ERROR OSUnRegisterDiscontigMem(IMG_VOID *pvCpuVAddr, IMG_UINT32 ui32Bytes
     return OSUnRegisterMem(pvCpuVAddr, ui32Bytes, ui32Flags, hOSMemHandle);
 }
 
+/*!
+******************************************************************************
+ @Function     OSReservePhys
+ @Description Registers physical memory for user mode mapping
+ @Output    ppvCpuVAddr
+ @Output    phOsMemHandle handle to registered memory
+ @Return TRUE on success, else FALSE
+******************************************************************************/
 PVRSRV_ERROR
 OSReservePhys(IMG_CPU_PHYADDR BasePAddr,
               IMG_UINT32 ui32Bytes,
               IMG_UINT32 ui32MappingFlags,
+              IMG_HANDLE hBMHandle,
               IMG_VOID **ppvCpuVAddr,
               IMG_HANDLE *phOSMemHandle)
 {
     LinuxMemArea *psLinuxMemArea;
 
 #if 0
-    
+    /* For debug: force all OSReservePhys reservations to have a kernel
+     * virtual address */
     if(ui32MappingFlags & PVRSRV_HAP_SINGLE_PROCESS)
     {
         ui32MappingFlags &= ~PVRSRV_HAP_SINGLE_PROCESS;
@@ -1313,7 +1892,10 @@ OSReservePhys(IMG_CPU_PHYADDR BasePAddr,
     {
         case PVRSRV_HAP_KERNEL_ONLY:
         {
-            
+            /* Currently PVRSRV_HAP_KERNEL_ONLY implies that a kernel virtual
+             * mapping is required for the allocation and no user virtual
+             * mappings are allowed: Note these eat into our limited kernel
+             * virtual address space */
             psLinuxMemArea = NewIORemapLinuxMemArea(BasePAddr, ui32Bytes, ui32MappingFlags);
             if(!psLinuxMemArea)
             {
@@ -1323,7 +1905,8 @@ OSReservePhys(IMG_CPU_PHYADDR BasePAddr,
         }
         case PVRSRV_HAP_SINGLE_PROCESS:
         {
-            
+            /* Currently this implies that we dont need a kernel virtual
+             * mapping, but will need a user space virtual mapping */
             psLinuxMemArea = NewIOLinuxMemArea(BasePAddr, ui32Bytes, ui32MappingFlags);
             if(!psLinuxMemArea)
             {
@@ -1334,9 +1917,18 @@ OSReservePhys(IMG_CPU_PHYADDR BasePAddr,
         }
         case PVRSRV_HAP_MULTI_PROCESS:
         {
-            
+            /* Currently PVRSRV_HAP_MULTI_PROCESS implies that we need a kernel
+             * virtual mapping and potentially multiple user space virtual mappings.
+             * Beware that the kernel virtual address space is a limited resource.
+             */
 #if defined(VIVT_CACHE) || defined(__sh__)
-            
+            /* 
+             * ARM9 caches are tagged with virtual pages, not physical. As we are going to
+             * share this memory in different address spaces, we don't want it to be cached.
+             * ARM11 has physical tagging, so we can cache this memory without fear of virtual
+             * address aliasing in the TLB, as long as the kernel supports cache colouring for
+             * VIPT architectures.
+             */
             ui32MappingFlags &= ~PVRSRV_HAP_CACHED;
 #endif
             psLinuxMemArea = NewIORemapLinuxMemArea(BasePAddr, ui32Bytes, ui32MappingFlags);
@@ -1354,6 +1946,16 @@ OSReservePhys(IMG_CPU_PHYADDR BasePAddr,
             return PVRSRV_ERROR_INVALID_FLAGS;
     }
 
+       /*
+               In case of sparse mapping we need to handle back to the BM as it
+               knows the mapping info
+       */
+       if (ui32MappingFlags & PVRSRV_MEM_SPARSE)
+       {
+               PVR_ASSERT(hBMHandle != IMG_NULL);
+               psLinuxMemArea->hBMHandle = hBMHandle;
+       }
+
     *phOSMemHandle = (IMG_HANDLE)psLinuxMemArea;
     *ppvCpuVAddr = LinuxMemAreaToCpuVAddr(psLinuxMemArea);
 
@@ -1362,6 +1964,12 @@ OSReservePhys(IMG_CPU_PHYADDR BasePAddr,
     return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+ @Function     OSUnReservePhys
+ @Description UnRegisters physical memory for user mode mapping
+ @Return TRUE on success, else FALSE
+******************************************************************************/
 PVRSRV_ERROR
 OSUnReservePhys(IMG_VOID *pvCpuVAddr,
                 IMG_UINT32 ui32Bytes,
@@ -1406,6 +2014,14 @@ OSUnReservePhys(IMG_VOID *pvCpuVAddr,
 }
 
 
+/*!
+******************************************************************************
+ @Function     OSBaseAllocContigMemory
+ @Description Allocate a block of contiguous virtual non-paged memory.
+ @Input     ui32Size - number of bytes to allocate
+ @Output    ppvLinAddr - pointer to variable that will receive the linear address of buffer
+ @Return PVRSRV_OK if allocation successed else returns PVRSRV_ERROR_OUT_OF_MEMORY
+ **************************************************************************/
 PVRSRV_ERROR OSBaseAllocContigMemory(IMG_UINT32 ui32Size, IMG_CPU_VIRTADDR *pvLinAddr, IMG_CPU_PHYADDR *psPhysAddr)
 {
 #if !defined(NO_HARDWARE)
@@ -1416,6 +2032,13 @@ PVRSRV_ERROR OSBaseAllocContigMemory(IMG_UINT32 ui32Size, IMG_CPU_VIRTADDR *pvLi
 
     return PVRSRV_ERROR_OUT_OF_MEMORY;
 #else
+/*
+ * On Linux, the returned virtual address should be used for CPU access,
+ * and not be remapped into the CPU virtual address using ioremap.  The fact
+ * that the RAM is being managed by the kernel, and already has a virtual
+ * address, seems to lead to problems when the attributes of the memory are
+ * changed in the ioremap call (such as from cached to non-cached).
+ */
     IMG_VOID *pvKernLinAddr;
 
 #if defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
@@ -1433,10 +2056,16 @@ PVRSRV_ERROR OSBaseAllocContigMemory(IMG_UINT32 ui32Size, IMG_CPU_VIRTADDR *pvLi
     psPhysAddr->uiAddr = virt_to_phys(pvKernLinAddr);
 
     return PVRSRV_OK;
-#endif 
+#endif /* !defined(NO_HARDWARE) */
 }
 
 
+/*!
+******************************************************************************
+ @Function     OSBaseFreeContigMemory
+ @Description Frees memory allocated with OSBaseAllocContigMemory
+ @Input     LinAddr - pointer to buffer allocated with OSBaseAllocContigMemory
+ **************************************************************************/
 PVRSRV_ERROR OSBaseFreeContigMemory(IMG_UINT32 ui32Size, IMG_CPU_VIRTADDR pvLinAddr, IMG_CPU_PHYADDR psPhysAddr)
 {
 #if !defined(NO_HARDWARE)
@@ -1454,6 +2083,25 @@ PVRSRV_ERROR OSBaseFreeContigMemory(IMG_UINT32 ui32Size, IMG_CPU_VIRTADDR pvLinA
     return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSWriteHWReg
+ @Description 
+ register access function
+
+ @input pvLinRegBaseAddr :     lin addr of register block base
+
+ @input ui32Offset :    
+
+ @input ui32Value :    
+ @Return   none
+
+******************************************************************************/
+
 IMG_UINT32 OSReadHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset)
 {
 #if !defined(NO_HARDWARE)
@@ -1474,6 +2122,22 @@ IMG_VOID OSWriteHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset, IMG_UIN
 
 #if defined(CONFIG_PCI) && (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,14))
 
+/*!
+******************************************************************************
+
+ @Function     OSPCISetDev
+ @Description 
+ Set a PCI device for subsequent use.
+
+ @input pvPCICookie :  Pointer to OS specific PCI structure/cookie
+
+ @input eFlags :       Flags
+
+ @Return   Pointer to PCI device handle
+
+******************************************************************************/
 PVRSRV_PCI_DEV_HANDLE OSPCISetDev(IMG_VOID *pvPCICookie, HOST_PCI_INIT_FLAGS eFlags)
 {
     int err;
@@ -1499,26 +2163,26 @@ PVRSRV_PCI_DEV_HANDLE OSPCISetDev(IMG_VOID *pvPCICookie, HOST_PCI_INIT_FLAGS eFl
         return IMG_NULL;
     }
 
-    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_BUS_MASTER)    
+    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_BUS_MASTER)   /* PRQA S 3358 */ /* misuse of enums */
     {
         pci_set_master(psPVRPCI->psPCIDev);
     }
 
-    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_MSI)           
+    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_MSI)          /* PRQA S 3358 */ /* misuse of enums */
     {
 #if defined(CONFIG_PCI_MSI)
         err = pci_enable_msi(psPVRPCI->psPCIDev);
         if (err != 0)
         {
             PVR_DPF((PVR_DBG_WARNING, "OSPCISetDev: Couldn't enable MSI (%d)", err));
-            psPVRPCI->ePCIFlags &= ~HOST_PCI_INIT_FLAG_MSI;     
+            psPVRPCI->ePCIFlags &= ~HOST_PCI_INIT_FLAG_MSI;    /* PRQA S 1474,3358,4130 */ /* misuse of enums */
         }
 #else
         PVR_DPF((PVR_DBG_WARNING, "OSPCISetDev: MSI support not enabled in the kernel"));
 #endif
     }
 
-    
+    /* Initialise the PCI resource tracking array */
     for (i = 0; i < DEVICE_COUNT_RESOURCE; i++)
     {
         psPVRPCI->abPCIResourceInUse[i] = IMG_FALSE;
@@ -1527,12 +2191,30 @@ PVRSRV_PCI_DEV_HANDLE OSPCISetDev(IMG_VOID *pvPCICookie, HOST_PCI_INIT_FLAGS eFl
     return (PVRSRV_PCI_DEV_HANDLE)psPVRPCI;
 }
 
-PVRSRV_PCI_DEV_HANDLE OSPCIAcquireDev(IMG_UINT16 ui16VendorID, IMG_UINT16 ui16DeviceID, HOST_PCI_INIT_FLAGS eFlags)
-{
-    struct pci_dev *psPCIDev;
+/*!
+******************************************************************************
 
-    psPCIDev = pci_get_device(ui16VendorID, ui16DeviceID, NULL);
-    if (psPCIDev == NULL)
+ @Function     OSPCIAcquireDev
+ @Description 
+ Acquire a PCI device for subsequent use.
+
+ @input ui16VendorID : Vendor PCI ID
+
+ @input ui16VendorID : Device PCI ID
+
+ @input eFlags :       Flags
+
+ @Return   PVESRV_ERROR
+
+******************************************************************************/
+PVRSRV_PCI_DEV_HANDLE OSPCIAcquireDev(IMG_UINT16 ui16VendorID, IMG_UINT16 ui16DeviceID, HOST_PCI_INIT_FLAGS eFlags)
+{
+    struct pci_dev *psPCIDev;
+
+    psPCIDev = pci_get_device(ui16VendorID, ui16DeviceID, NULL);
+    if (psPCIDev == NULL)
     {
         PVR_DPF((PVR_DBG_ERROR, "OSPCIAcquireDev: Couldn't acquire device"));
         return IMG_NULL;
@@ -1541,6 +2223,22 @@ PVRSRV_PCI_DEV_HANDLE OSPCIAcquireDev(IMG_UINT16 ui16VendorID, IMG_UINT16 ui16De
     return OSPCISetDev((IMG_VOID *)psPCIDev, eFlags);
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIIRQ
+ @Description 
+ Get the interrupt number for the device.
+
+ @input hPVRPCI :      PCI device handle
+
+ @input pui32IRQ :     Pointer to where the interrupt number should be returned
+
+ @Return   PVESRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR OSPCIIRQ(PVRSRV_PCI_DEV_HANDLE hPVRPCI, IMG_UINT32 *pui32IRQ)
 {
     PVR_PCI_DEV *psPVRPCI = (PVR_PCI_DEV *)hPVRPCI;
@@ -1550,6 +2248,7 @@ PVRSRV_ERROR OSPCIIRQ(PVRSRV_PCI_DEV_HANDLE hPVRPCI, IMG_UINT32 *pui32IRQ)
     return PVRSRV_OK;
 }
 
+/* Functions supported by OSPCIAddrRangeFunc */
 enum HOST_PCI_ADDR_RANGE_FUNC
 {
     HOST_PCI_ADDR_RANGE_FUNC_LEN,
@@ -1559,6 +2258,24 @@ enum HOST_PCI_ADDR_RANGE_FUNC
     HOST_PCI_ADDR_RANGE_FUNC_RELEASE
 };
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIAddrRangeFunc
+ @Description 
+ Internal support function for various address range related functions
+
+ @input eFunc :        Function to perform
+
+ @input hPVRPCI :      PCI device handle
+
+ @input ui32Index :    Address range index
+
+ @Return   function dependent
+
+******************************************************************************/
 static IMG_UINT32 OSPCIAddrRangeFunc(enum HOST_PCI_ADDR_RANGE_FUNC eFunc,
                                      PVRSRV_PCI_DEV_HANDLE hPVRPCI,
                                      IMG_UINT32 ui32Index)
@@ -1608,32 +2325,126 @@ static IMG_UINT32 OSPCIAddrRangeFunc(enum HOST_PCI_ADDR_RANGE_FUNC eFunc,
     return 0;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIAddrRangeLen
+ @Description 
+ Returns length of a given address range length
+
+ @input hPVRPCI :      PCI device handle
+
+ @input ui32Index :    Address range index
+
+ @Return   Length of address range, or 0 if no such range
+
+******************************************************************************/
 IMG_UINT32 OSPCIAddrRangeLen(PVRSRV_PCI_DEV_HANDLE hPVRPCI, IMG_UINT32 ui32Index)
 {
     return OSPCIAddrRangeFunc(HOST_PCI_ADDR_RANGE_FUNC_LEN, hPVRPCI, ui32Index); 
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIAddrRangeStart
+ @Description 
+ Returns the start of a given address range
+
+ @input hPVRPCI :      PCI device handle
+
+ @input ui32Index :    Address range index
+
+ @Return   Start of address range, or 0 if no such range
+
+******************************************************************************/
 IMG_UINT32 OSPCIAddrRangeStart(PVRSRV_PCI_DEV_HANDLE hPVRPCI, IMG_UINT32 ui32Index)
 {
     return OSPCIAddrRangeFunc(HOST_PCI_ADDR_RANGE_FUNC_START, hPVRPCI, ui32Index); 
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIAddrRangeEnd
+ @Description 
+ Returns the end of a given address range
+
+ @input hPVRPCI :      PCI device handle"ayy
+
+ @input ui32Index :    Address range index
+
+ @Return   End of address range, or 0 if no such range
+
+******************************************************************************/
 IMG_UINT32 OSPCIAddrRangeEnd(PVRSRV_PCI_DEV_HANDLE hPVRPCI, IMG_UINT32 ui32Index)
 {
     return OSPCIAddrRangeFunc(HOST_PCI_ADDR_RANGE_FUNC_END, hPVRPCI, ui32Index); 
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIRequestAddrRange
+ @Description 
+ Request a given address range index for subsequent use
+
+ @input hPVRPCI :      PCI device handle
+
+ @input ui32Index :    Address range index
+
+ @Return   PVESRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR OSPCIRequestAddrRange(PVRSRV_PCI_DEV_HANDLE hPVRPCI,
                                    IMG_UINT32 ui32Index)
 {
     return OSPCIAddrRangeFunc(HOST_PCI_ADDR_RANGE_FUNC_REQUEST, hPVRPCI, ui32Index) == 0 ? PVRSRV_ERROR_PCI_CALL_FAILED : PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIReleaseAddrRange
+ @Description 
+ Release a given address range that is no longer being used
+
+ @input hPVRPCI :      PCI device handle
+
+ @input ui32Index :    Address range index
+
+ @Return   PVESRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR OSPCIReleaseAddrRange(PVRSRV_PCI_DEV_HANDLE hPVRPCI, IMG_UINT32 ui32Index)
 {
     return OSPCIAddrRangeFunc(HOST_PCI_ADDR_RANGE_FUNC_RELEASE, hPVRPCI, ui32Index) == 0 ? PVRSRV_ERROR_PCI_CALL_FAILED : PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIReleaseDev
+ @Description 
+ Release a PCI device that is no longer being used
+
+ @input hPVRPCI :      PCI device handle
+
+ @Return   PVESRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR OSPCIReleaseDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
 {
     PVR_PCI_DEV *psPVRPCI = (PVR_PCI_DEV *)hPVRPCI;
@@ -1641,7 +2452,7 @@ PVRSRV_ERROR OSPCIReleaseDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
 
     PVR_TRACE(("OSPCIReleaseDev"));
 
-    
+    /* Release all PCI regions that are currently in use */
     for (i = 0; i < DEVICE_COUNT_RESOURCE; i++)
     {
         if (psPVRPCI->abPCIResourceInUse[i])
@@ -1653,14 +2464,14 @@ PVRSRV_ERROR OSPCIReleaseDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
     }
 
 #if defined(CONFIG_PCI_MSI)
-    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_MSI)           
+    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_MSI)          /* PRQA S 3358 */ /* misuse of enums */
     {
         pci_disable_msi(psPVRPCI->psPCIDev);
     }
 #endif
 
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,29))
-    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_BUS_MASTER)    
+    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_BUS_MASTER)   /* PRQA S 3358 */ /* misuse of enums */
     {
         pci_clear_master(psPVRPCI->psPCIDev);
     }
@@ -1668,11 +2479,25 @@ PVRSRV_ERROR OSPCIReleaseDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
     pci_disable_device(psPVRPCI->psPCIDev);
 
     OSFreeMem(PVRSRV_OS_PAGEABLE_HEAP, sizeof(*psPVRPCI), (IMG_VOID *)psPVRPCI, IMG_NULL);
-       
+       /*not nulling pointer, copy on stack*/
 
     return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCISuspendDev
+ @Description 
+ Prepare PCI device to be turned off by power management
+
+ @input hPVRPCI :      PCI device handle
+
+ @Return   PVESRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR OSPCISuspendDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
 {
     PVR_PCI_DEV *psPVRPCI = (PVR_PCI_DEV *)hPVRPCI;
@@ -1681,7 +2506,7 @@ PVRSRV_ERROR OSPCISuspendDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
 
     PVR_TRACE(("OSPCISuspendDev"));
 
-    
+    /* Release all PCI regions that are currently in use */
     for (i = 0; i < DEVICE_COUNT_RESOURCE; i++)
     {
         if (psPVRPCI->abPCIResourceInUse[i])
@@ -1718,6 +2543,24 @@ PVRSRV_ERROR OSPCISuspendDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
     return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSPCIResumeDev
+ @Description 
+ Prepare a PCI device to be resumed by power management
+
+ @input hPVRPCI :      PCI device handle
+
+ @input pvPCICookie :  Pointer to OS specific PCI structure/cookie
+
+ @input eFlags :       Flags
+
+ @Return   PVESRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR OSPCIResumeDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
 {
     PVR_PCI_DEV *psPVRPCI = (PVR_PCI_DEV *)hPVRPCI;
@@ -1760,10 +2603,10 @@ PVRSRV_ERROR OSPCIResumeDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
         return PVRSRV_ERROR_PCI_CALL_FAILED;
     }
 
-    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_BUS_MASTER)    
+    if (psPVRPCI->ePCIFlags & HOST_PCI_INIT_FLAG_BUS_MASTER)   /* PRQA S 3358 */ /* misuse of enums */
         pci_set_master(psPVRPCI->psPCIDev);
 
-    
+    /* Restore the PCI resource tracking array */
     for (i = 0; i < DEVICE_COUNT_RESOURCE; i++)
     {
         if (psPVRPCI->abPCIResourceInUse[i])
@@ -1780,10 +2623,11 @@ PVRSRV_ERROR OSPCIResumeDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI)
     return PVRSRV_OK;
 }
 
-#endif 
+#endif /* #if defined(CONFIG_PCI) && (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0)) */
 
 #define        OS_MAX_TIMERS   8
 
+/* Timer callback strucure used by OSAddTimer */
 typedef struct TIMER_CALLBACK_DATA_TAG
 {
     IMG_BOOL                   bInUse;
@@ -1806,8 +2650,13 @@ static TIMER_CALLBACK_DATA sTimers[OS_MAX_TIMERS];
 #if defined(PVR_LINUX_TIMERS_USING_WORKQUEUES) || defined(PVR_LINUX_TIMERS_USING_SHARED_WORKQUEUE)
 DEFINE_MUTEX(sTimerStructLock);
 #else
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,39))
+/* The lock is used to control access to sTimers */
+/* PRQA S 0671,0685 1 */ /* C99 macro not understood by QAC */
 static spinlock_t sTimerStructLock = SPIN_LOCK_UNLOCKED;
+#else
+static DEFINE_SPINLOCK(sTimerStructLock);
+#endif
 #endif
 
 static void OSTimerCallbackBody(TIMER_CALLBACK_DATA *psTimerCBData)
@@ -1815,14 +2664,28 @@ static void OSTimerCallbackBody(TIMER_CALLBACK_DATA *psTimerCBData)
     if (!psTimerCBData->bActive)
         return;
 
-    
+    /* call timer callback */
     psTimerCBData->pfnTimerFunc(psTimerCBData->pvData);
     
-    
+    /* reset timer */
     mod_timer(&psTimerCBData->sTimer, psTimerCBData->ui32Delay + jiffies);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     OSTimerCallbackWrapper
+ @Description 
+ OS specific timer callback wrapper function
+ @Input    ui32Data : timer callback data
+
+ @Return   NONE
+
+******************************************************************************/
 static IMG_VOID OSTimerCallbackWrapper(IMG_UINT32 ui32Data)
 {
     TIMER_CALLBACK_DATA        *psTimerCBData = (TIMER_CALLBACK_DATA*)ui32Data;
@@ -1854,6 +2717,24 @@ static void OSTimerWorkQueueCallBack(struct work_struct *psWork)
 }
 #endif
 
+/*!
+******************************************************************************
+
+ @Function     OSAddTimer
+ @Description 
+ OS specific function to install a timer callback
+ @Input    pfnTimerFunc : timer callback
+
+ @Input    *pvData :callback data
+ @Input                ui32MsTimeout: callback period 
+
+ @Return   IMG_HANDLE  : valid handle success, NULL failure
+
+******************************************************************************/
 IMG_HANDLE OSAddTimer(PFN_TIMER_FUNC pfnTimerFunc, IMG_VOID *pvData, IMG_UINT32 ui32MsTimeout)
 {
     TIMER_CALLBACK_DATA        *psTimerCBData;
@@ -1862,14 +2743,14 @@ IMG_HANDLE OSAddTimer(PFN_TIMER_FUNC pfnTimerFunc, IMG_VOID *pvData, IMG_UINT32
     unsigned long              ulLockFlags;
 #endif
 
-    
+    /* check callback */
     if(!pfnTimerFunc)
     {
         PVR_DPF((PVR_DBG_ERROR, "OSAddTimer: passed invalid callback"));               
         return IMG_NULL;               
     }
     
-    
+    /* Allocate timer callback data structure */
 #if defined(PVR_LINUX_TIMERS_USING_WORKQUEUES) || defined(PVR_LINUX_TIMERS_USING_SHARED_WORKQUEUE)
     mutex_lock(&sTimerStructLock);
 #else
@@ -1899,17 +2780,19 @@ IMG_HANDLE OSAddTimer(PFN_TIMER_FUNC pfnTimerFunc, IMG_VOID *pvData, IMG_UINT32
     psTimerCBData->pvData = pvData;
     psTimerCBData->bActive = IMG_FALSE;
     
-    
-
-
+    /*
+        HZ = ticks per second
+        ui32MsTimeout = required ms delay
+        ticks = (Hz * ui32MsTimeout) / 1000    
+    */
     psTimerCBData->ui32Delay = ((HZ * ui32MsTimeout) < 1000)
                                 ?      1
                                 :      ((HZ * ui32MsTimeout) / 1000);
-    
+    /* initialise object */
     init_timer(&psTimerCBData->sTimer);
     
-    
-     
+    /* setup timer object */
+    /* PRQA S 0307,0563 1 */ /* ignore warning about inconpartible ptr casting */
     psTimerCBData->sTimer.function = (IMG_VOID *)OSTimerCallbackWrapper;
     psTimerCBData->sTimer.data = (IMG_UINT32)psTimerCBData;
     
@@ -1926,6 +2809,20 @@ static inline TIMER_CALLBACK_DATA *GetTimerStructure(IMG_HANDLE hTimer)
     return &sTimers[ui32i];
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSRemoveTimer
+ @Description 
+ OS specific function to remove a timer callback
+ @Input    hTimer : timer handle
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR OSRemoveTimer (IMG_HANDLE hTimer)
 {
     TIMER_CALLBACK_DATA *psTimerCBData = GetTimerStructure(hTimer);
@@ -1933,13 +2830,27 @@ PVRSRV_ERROR OSRemoveTimer (IMG_HANDLE hTimer)
     PVR_ASSERT(psTimerCBData->bInUse);
     PVR_ASSERT(!psTimerCBData->bActive);
 
-    
+    /* free timer callback data struct */
     psTimerCBData->bInUse = IMG_FALSE;
     
     return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     OSEnableTimer
+ @Description 
+ OS specific function to enable a timer callback
+ @Input    hTimer : timer handle
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR OSEnableTimer (IMG_HANDLE hTimer)
 {
     TIMER_CALLBACK_DATA *psTimerCBData = GetTimerStructure(hTimer);
@@ -1947,19 +2858,33 @@ PVRSRV_ERROR OSEnableTimer (IMG_HANDLE hTimer)
     PVR_ASSERT(psTimerCBData->bInUse);
     PVR_ASSERT(!psTimerCBData->bActive);
 
-    
+    /* Start timer arming */
     psTimerCBData->bActive = IMG_TRUE;
 
-    
+    /* set the expire time */
     psTimerCBData->sTimer.expires = psTimerCBData->ui32Delay + jiffies;
 
-    
+    /* Add the timer to the list */
     add_timer(&psTimerCBData->sTimer);
     
     return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     OSDisableTimer
+ @Description 
+ OS specific function to disable a timer callback
+ @Input    hTimer : timer handle
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR OSDisableTimer (IMG_HANDLE hTimer)
 {
     TIMER_CALLBACK_DATA *psTimerCBData = GetTimerStructure(hTimer);
@@ -1967,7 +2892,7 @@ PVRSRV_ERROR OSDisableTimer (IMG_HANDLE hTimer)
     PVR_ASSERT(psTimerCBData->bInUse);
     PVR_ASSERT(psTimerCBData->bActive);
 
-    
+    /* Stop timer from arming */
     psTimerCBData->bActive = IMG_FALSE;
     smp_mb();
 
@@ -1978,11 +2903,17 @@ PVRSRV_ERROR OSDisableTimer (IMG_HANDLE hTimer)
     flush_scheduled_work();
 #endif
 
-    
+    /* remove timer */
     del_timer_sync(&psTimerCBData->sTimer);    
     
 #if defined(PVR_LINUX_TIMERS_USING_WORKQUEUES)
-    
+    /*
+     * This second flush is to catch the case where the timer ran
+     * before we managed to delete it, in which case, it will have
+     * queued more work for the workqueue.  Since the bActive flag
+     * has been cleared, this second flush won't result in the
+     * timer being rearmed.
+     */
     flush_workqueue(psTimerWorkQueue);
 #endif
 #if defined(PVR_LINUX_TIMERS_USING_SHARED_WORKQUEUE)
@@ -1993,6 +2924,22 @@ PVRSRV_ERROR OSDisableTimer (IMG_HANDLE hTimer)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     OSEventObjectCreateKM
+ @Description 
+ OS specific function to create an event object
+ @Input    pszName : Globally unique event object name (if null name must be autogenerated)
+ @Output   psEventObject : OS event object info structure
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR OSEventObjectCreateKM(const IMG_CHAR *pszName, PVRSRV_EVENTOBJECT_KM *psEventObject)
 #else
@@ -2006,12 +2953,12 @@ PVRSRV_ERROR OSEventObjectCreateKM(const IMG_CHAR *pszName, PVRSRV_EVENTOBJECT *
     {
         if(pszName)
         {
-            
+            /* copy over the event object name */
             strncpy(psEventObject->szName, pszName, EVENTOBJNAME_MAXLENGTH);
         }
         else
         {
-               
+            /* autogenerate a name */  
             static IMG_UINT16 ui16NameIndex = 0;                       
 #if defined (SUPPORT_SID_INTERFACE)
             snprintf(psEventObject->szName, EVENTOBJNAME_MAXLENGTH, "PVRSRV_EVENTOBJECT_KM_%d", ui16NameIndex++);
@@ -2037,6 +2984,20 @@ PVRSRV_ERROR OSEventObjectCreateKM(const IMG_CHAR *pszName, PVRSRV_EVENTOBJECT *
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     OSEventObjectDestroyKM
+ @Description 
+ OS specific function to destroy an event object
+ @Input    psEventObject : OS event object info structure
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR OSEventObjectDestroyKM(PVRSRV_EVENTOBJECT_KM *psEventObject)
 #else
@@ -2066,6 +3027,20 @@ PVRSRV_ERROR OSEventObjectDestroyKM(PVRSRV_EVENTOBJECT *psEventObject)
     return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSEventObjectWaitKM
+ @Description 
+ OS specific function to wait for an event object.  Called from client
+ @Input    hOSEventKM : OS and kernel specific handle to event object
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR OSEventObjectWaitKM(IMG_HANDLE hOSEventKM)
 {
     PVRSRV_ERROR eError;
@@ -2083,6 +3058,21 @@ PVRSRV_ERROR OSEventObjectWaitKM(IMG_HANDLE hOSEventKM)
     return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSEventObjectOpenKM
+ @Description 
+ OS specific function to open an event object.  Called from client
+ @Input    psEventObject : Pointer to an event object
+ @Output   phOSEvent : OS and kernel specific handle to event object
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR OSEventObjectOpenKM(PVRSRV_EVENTOBJECT_KM *psEventObject,
 #else
@@ -2110,6 +3100,22 @@ PVRSRV_ERROR OSEventObjectOpenKM(PVRSRV_EVENTOBJECT *psEventObject,
     return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSEventObjectCloseKM
+ @Description 
+ OS specific function to close an event object.  Called from client
+ @Input    psEventObject : Pointer to an event object
+ @OInput   hOSEventKM : OS and kernel specific handle to event object
+
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 #if defined (SUPPORT_SID_INTERFACE)
 PVRSRV_ERROR OSEventObjectCloseKM(PVRSRV_EVENTOBJECT_KM *psEventObject,
 #else
@@ -2138,6 +3144,20 @@ PVRSRV_ERROR OSEventObjectCloseKM(PVRSRV_EVENTOBJECT *psEventObject,
     
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSEventObjectSignalKM
+ @Description 
+ OS specific function to 'signal' an event object.  Called from L/MISR
+ @Input    hOSEventKM : OS and kernel specific handle to event object
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR OSEventObjectSignalKM(IMG_HANDLE hOSEventKM)
 {
     PVRSRV_ERROR eError;
@@ -2155,11 +3175,43 @@ PVRSRV_ERROR OSEventObjectSignalKM(IMG_HANDLE hOSEventKM)
     return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSProcHasPrivSrvInit
+ @Description 
+ Does the process have sufficient privileges to initialise services?
+ @Input    none
+
+ @Return   IMG_BOOL :
+
+******************************************************************************/
 IMG_BOOL OSProcHasPrivSrvInit(IMG_VOID)
 {
     return (capable(CAP_SYS_MODULE) != 0) ? IMG_TRUE : IMG_FALSE;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSCopyToUser
+ @Description 
+ Copy a block of data into user space
+ @Input    pvSrc
+ @Output    pvDest
+
+ @Input        ui32Bytes 
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR OSCopyToUser(IMG_PVOID pvProcess, 
                           IMG_VOID *pvDest, 
                           IMG_VOID *pvSrc, 
@@ -2173,6 +3225,24 @@ PVRSRV_ERROR OSCopyToUser(IMG_PVOID pvProcess,
         return PVRSRV_ERROR_FAILED_TO_COPY_VIRT_MEMORY;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSCopyFromUser
+ @Description 
+ Copy a block of data from the user space
+ @Output    pvDest
+ @Input    pvSrc
+
+ @Input        ui32Bytes 
+
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR OSCopyFromUser( IMG_PVOID pvProcess, 
                              IMG_VOID *pvDest, 
                              IMG_VOID *pvSrc, 
@@ -2186,6 +3256,24 @@ PVRSRV_ERROR OSCopyFromUser( IMG_PVOID pvProcess,
         return PVRSRV_ERROR_FAILED_TO_COPY_VIRT_MEMORY;
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSAccessOK
+ @Description 
+ Checks if a user space pointer is valide
+ @Input    eVerification
+
+ @Input    pvUserPtr
+
+ @Input        ui32Bytes 
+
+ @Return   IMG_BOOL :
+
+******************************************************************************/
 IMG_BOOL OSAccessOK(IMG_VERIFY_TEST eVerification, IMG_VOID *pvUserPtr, IMG_UINT32 ui32Bytes)
 {
     IMG_INT linuxType;
@@ -2226,6 +3314,28 @@ typedef struct _sWrapMemInfo_
 } sWrapMemInfo;
 
 
+/*!
+******************************************************************************
+
+ @Function     *CPUVAddrToPFN
+ @Description 
+ Find the PFN associated with a given CPU virtual address, and return
+ the associated page structure, if it exists.
+ The page in question must be present (i.e. no fault handling required),
+ and must be writable.  A get_page is done on the returned page structure.
+ @Input    psVMArea - pointer to VM area structure
+       ulCPUVAddr - CPU virtual address
+       pulPFN - Pointer to returned PFN.
+       ppsPAge - Pointer to returned page structure pointer.
+
+ @Output   *pulPFN - Set to PFN
+          *ppsPage - Pointer to the page structure if present, else NULL.
+ @Return   IMG_TRUE if PFN lookup was succesful.
+
+******************************************************************************/
 static IMG_BOOL CPUVAddrToPFN(struct vm_area_struct *psVMArea, IMG_UINT32 ulCPUVAddr, IMG_UINT32 *pulPFN, struct page **ppsPage)
 {
 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,10))
@@ -2275,6 +3385,20 @@ static IMG_BOOL CPUVAddrToPFN(struct vm_area_struct *psVMArea, IMG_UINT32 ulCPUV
 #endif
 }
 
+/*!
+******************************************************************************
+
+ @Function     OSReleasePhysPageAddr
+ @Description 
+ Release wrapped memory.
+
+ @Input    hOSWrapMem : Driver cookie
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR OSReleasePhysPageAddr(IMG_HANDLE hOSWrapMem)
 {
     sWrapMemInfo *psInfo = (sWrapMemInfo *)hOSWrapMem;
@@ -2303,7 +3427,12 @@ PVRSRV_ERROR OSReleasePhysPageAddr(IMG_HANDLE hOSWrapMem)
 
                PVR_ASSERT(psPage != NULL);
 
-                
+                /*
+                * If the number of pages mapped is not the same as
+                * the number of pages in the address range, then
+                * get_user_pages must have failed, so we are cleaning
+                * up after failure, and the pages can't be dirty.
+                */
                if (psInfo->iNumPagesMapped == psInfo->iNumPages)
                {
                     if (!PageReserved(psPage))
@@ -2349,6 +3478,59 @@ PVRSRV_ERROR OSReleasePhysPageAddr(IMG_HANDLE hOSWrapMem)
     return PVRSRV_OK;
 }
 
+#if defined(CONFIG_TI_TILER)
+
+static IMG_UINT32 CPUAddrToTilerPhy(IMG_UINT32 uiAddr)
+{
+       IMG_UINT32 ui32PhysAddr = 0;
+       pte_t *ptep, pte;
+       pgd_t *pgd;
+       pmd_t *pmd;
+
+       pgd = pgd_offset(current->mm, uiAddr);
+       if (pgd_none(*pgd) || pgd_bad(*pgd))
+               goto err_out;
+
+       pmd = pmd_offset(pgd, uiAddr);
+       if (pmd_none(*pmd) || pmd_bad(*pmd))
+               goto err_out;
+
+       ptep = pte_offset_map(pmd, uiAddr);
+       if (!ptep)
+               goto err_out;
+
+       pte = *ptep;
+       if (!pte_present(pte))
+               goto err_out;
+
+       ui32PhysAddr = (pte & PAGE_MASK) | (~PAGE_MASK & uiAddr);
+
+       /* If the physAddr is not in the TILER physical range
+        * then we don't proceed.
+        */
+       if (ui32PhysAddr < 0x60000000 && ui32PhysAddr > 0x7fffffff)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "CPUAddrToTilerPhy: Not in tiler range"));
+               ui32PhysAddr = 0;
+               goto err_out;
+       }
+
+err_out:
+       return ui32PhysAddr;
+}
+
+#endif /* defined(CONFIG_TI_TILER) */
+
+/*!
+******************************************************************************
+
+ @Function     OSAcquirePhysPageAddr
+ @Description 
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr, 
                                     IMG_UINT32 ui32Bytes, 
                                     IMG_SYS_PHYADDR *psSysPAddr,
@@ -2366,16 +3548,18 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
     sWrapMemInfo *psInfo = NULL;
     IMG_BOOL bHavePageStructs = IMG_FALSE;
     IMG_BOOL bHaveNoPageStructs = IMG_FALSE;
-    IMG_BOOL bPFNMismatch = IMG_FALSE;
     IMG_BOOL bMMapSemHeld = IMG_FALSE;
     PVRSRV_ERROR eError = PVRSRV_ERROR_OUT_OF_MEMORY;
 
-    
+    /* Align start and end addresses to page boundaries */
     ulStartAddr = ulStartAddrOrig & PAGE_MASK;
     ulBeyondEndAddr = PAGE_ALIGN(ulBeyondEndAddrOrig);
     ulAddrRange = ulBeyondEndAddr - ulStartAddr;
 
-    
+    /*
+     * Check for address range calculation overflow, and attempts to wrap
+     * zero bytes.
+     */
     if (ulBeyondEndAddr <= ulStartAddr)
     {
         PVR_DPF((PVR_DBG_ERROR,
@@ -2384,7 +3568,7 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
         goto error;
     }
 
-    
+    /* Allocate information structure */
     psInfo = kmalloc(sizeof(*psInfo), GFP_KERNEL);
     if (psInfo == NULL)
     {
@@ -2402,7 +3586,7 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
     psInfo->iNumPages = (IMG_INT)(ulAddrRange >> PAGE_SHIFT);
     psInfo->iPageOffset = (IMG_INT)(ulStartAddrOrig & ~PAGE_MASK);
 
-    
+    /* Allocate physical address array */
     psInfo->psPhysAddr = kmalloc((size_t)psInfo->iNumPages * sizeof(*psInfo->psPhysAddr), GFP_KERNEL);
     if (psInfo->psPhysAddr == NULL)
     {
@@ -2412,7 +3596,7 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
     }
     memset(psInfo->psPhysAddr, 0, (size_t)psInfo->iNumPages * sizeof(*psInfo->psPhysAddr));
 
-    
+    /* Allocate page array */
     psInfo->ppsPages = kmalloc((size_t)psInfo->iNumPages * sizeof(*psInfo->ppsPages),  GFP_KERNEL);
     if (psInfo->ppsPages == NULL)
     {
@@ -2422,22 +3606,22 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
     }
     memset(psInfo->ppsPages, 0, (size_t)psInfo->iNumPages * sizeof(*psInfo->ppsPages));
 
-    
+    /* Default error code from now on */
     eError = PVRSRV_ERROR_BAD_MAPPING;
 
-    
+    /* Set the mapping type to aid clean up */
     psInfo->eType = WRAP_TYPE_GET_USER_PAGES;
 
-    
+    /* Lock down user memory */
     down_read(&current->mm->mmap_sem);
     bMMapSemHeld = IMG_TRUE;
 
-    
+    /* Get page list */
     psInfo->iNumPagesMapped = get_user_pages(current, current->mm, ulStartAddr, psInfo->iNumPages, 1, 0, psInfo->ppsPages, NULL);
 
     if (psInfo->iNumPagesMapped >= 0)
     {
-        
+        /* See if we got all the pages we wanted */
         if (psInfo->iNumPagesMapped != psInfo->iNumPages)
         {
             PVR_TRACE(("OSAcquirePhysPageAddr: Couldn't map all the pages needed (wanted: %d, got %d)", psInfo->iNumPages, psInfo->iNumPagesMapped));
@@ -2445,7 +3629,7 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
             goto error;
         }
 
-        
+        /* Build list of physical page addresses */
         for (i = 0; i < psInfo->iNumPages; i++)
         {
             IMG_CPU_PHYADDR CPUPhysAddr;
@@ -2470,13 +3654,18 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
 
     PVR_DPF((PVR_DBG_MESSAGE, "OSAcquirePhysPageAddr: get_user_pages failed (%d), using CPU page table", psInfo->iNumPagesMapped));
     
-    
+    /* Reset some fields */
     psInfo->eType = WRAP_TYPE_NULL;
     psInfo->iNumPagesMapped = 0;
     memset(psInfo->ppsPages, 0, (size_t)psInfo->iNumPages * sizeof(*psInfo->ppsPages));
 
-    
-    
+    /*
+     * get_user_pages didn't work.  If this is due to the address range
+     * representing memory mapped I/O, then we'll look for the pages
+     * in the appropriate memory region of the process.
+     */
+
+    /* Set the mapping type to aid clean up */
     psInfo->eType = WRAP_TYPE_FIND_VMA;
 
     psVMArea = find_vma(current->mm, ulStartAddrOrig);
@@ -2491,7 +3680,10 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
     psInfo->psVMArea = psVMArea;
 #endif
 
-    
+    /*
+     * find_vma locates a region with an end point past a given
+     * virtual address.  So check the address is actually in the region.
+     */
     if (ulStartAddrOrig < psVMArea->vm_start)
     {
         PVR_DPF((PVR_DBG_ERROR,
@@ -2499,7 +3691,7 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
         goto error;
     }
 
-    
+    /* Now check the end address is in range */
     if (ulBeyondEndAddrOrig > psVMArea->vm_end)
     {
         PVR_DPF((PVR_DBG_ERROR,
@@ -2507,7 +3699,7 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
         goto error;
     }
 
-    
+    /* Does the region represent memory mapped I/O? */
     if ((psVMArea->vm_flags & (VM_IO | VM_RESERVED)) != (VM_IO | VM_RESERVED))
     {
         PVR_DPF((PVR_DBG_ERROR,
@@ -2515,7 +3707,7 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
         goto error;
     }
 
-    
+    /* We require read and write access */
     if ((psVMArea->vm_flags & (VM_READ | VM_WRITE)) != (VM_READ | VM_WRITE))
     {
         PVR_DPF((PVR_DBG_ERROR,
@@ -2539,20 +3731,20 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
        }
        if (psInfo->ppsPages[i] == NULL)
        {
+#if defined(CONFIG_TI_TILER)
+               /* This could be tiler memory.*/
+               IMG_UINT32 ui32TilerAddr = CPUAddrToTilerPhy(ulAddr);
+               if (ui32TilerAddr)
+               {
+                       bHavePageStructs = IMG_TRUE;
+                       psInfo->iNumPagesMapped++;
+                       psInfo->psPhysAddr[i].uiAddr = ui32TilerAddr;
+                       psSysPAddr[i].uiAddr = ui32TilerAddr;
+                       continue;
+               }
+#endif /* defined(CONFIG_TI_TILER) */
 
            bHaveNoPageStructs = IMG_TRUE;
-
-#if defined(VM_PFNMAP)
-           if ((psVMArea->vm_flags & VM_PFNMAP) != 0)
-           {
-               IMG_UINT32 ulPFNRaw = ((ulAddr - psVMArea->vm_start) >> PAGE_SHIFT) + psVMArea->vm_pgoff;
-
-               if (ulPFNRaw != ulPFN)
-               {
-                       bPFNMismatch = IMG_TRUE;
-               }
-           }
-#endif
        }
        else
        {
@@ -2593,7 +3785,7 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
 
     if (!bHaveNoPageStructs)
     {
-       
+       /* The ideal case; every page has a page structure */
        goto exit;
     }
 
@@ -2606,34 +3798,21 @@ PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID *pvCPUVAddr,
        goto error;
     }
 
-    if (bPFNMismatch)
-    {
-        PVR_DPF((PVR_DBG_ERROR,
-            "OSAcquirePhysPageAddr: PFN calculation mismatch for VM_PFNMAP region"));
-       goto error;
-    }
-
 exit:
     PVR_ASSERT(bMMapSemHeld);
     up_read(&current->mm->mmap_sem);
 
-    
+    /* Return the cookie */
     *phOSWrapMem = (IMG_HANDLE)psInfo;
 
     if (bHaveNoPageStructs)
     {
-        PVR_DPF((PVR_DBG_WARNING,
+        PVR_DPF((PVR_DBG_MESSAGE,
             "OSAcquirePhysPageAddr: Region contains pages which can't be locked down (no page structures)"));
     }
 
     PVR_ASSERT(psInfo->eType != 0);
 
-#if 0
-    
-    
-    OSCleanCPUCacheRangeKM(pvCPUVAddr, (IMG_VOID *)((IMG_CHAR *)pvCPUVAddr + ui32Bytes));
-#endif
-
     return PVRSRV_OK;
 
 error:
@@ -2649,48 +3828,96 @@ error:
 }
 
 typedef void (*InnerCacheOp_t)(const void *pvStart, const void *pvEnd);
+
+#if defined(__arm__) && (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39))
+typedef void (*OuterCacheOp_t)(phys_addr_t uStart, phys_addr_t uEnd);
+#else
 typedef void (*OuterCacheOp_t)(unsigned long ulStart, unsigned long ulEnd);
+#endif
 
 #if defined(CONFIG_OUTER_CACHE)
 
-typedef unsigned long (*MemAreaToPhys_t)(LinuxMemArea *psLinuxMemArea,
+typedef IMG_BOOL (*MemAreaToPhys_t)(LinuxMemArea *psLinuxMemArea,
                                                                                 IMG_VOID *pvRangeAddrStart,
                                                                                 IMG_UINT32 ui32PageNumOffset,
-                                                                                IMG_UINT32 ui32PageNum);
-
-static unsigned long VMallocAreaToPhys(LinuxMemArea *psLinuxMemArea,
-                                                                          IMG_VOID *pvRangeAddrStart,
-                                                                          IMG_UINT32 ui32PageNumOffset,
-                                                                          IMG_UINT32 ui32PageNum)
+                                                                                IMG_UINT32 ui32PageNum,
+                                                                                unsigned long *pulStart);
+
+static IMG_BOOL VMallocAreaToPhys(LinuxMemArea *psLinuxMemArea,
+                                                                 IMG_VOID *pvRangeAddrStart,
+                                                                 IMG_UINT32 ui32PageNumOffset,
+                                                                 IMG_UINT32 ui32PageNum,
+                                                                 unsigned long *pulStart)
 {
-       return vmalloc_to_pfn(pvRangeAddrStart + ui32PageNum * PAGE_SIZE) << PAGE_SHIFT;
+       *pulStart = vmalloc_to_pfn(pvRangeAddrStart + ui32PageNum * PAGE_SIZE) << PAGE_SHIFT;
+       return IMG_TRUE;
 }
 
-static unsigned long ExternalKVAreaToPhys(LinuxMemArea *psLinuxMemArea,
-                                                                                 IMG_VOID *pvRangeAddrStart,
-                                                                                 IMG_UINT32 ui32PageNumOffset,
-                                                                                 IMG_UINT32 ui32PageNum)
+static IMG_BOOL ExternalKVAreaToPhys(LinuxMemArea *psLinuxMemArea,
+                                                                        IMG_VOID *pvRangeAddrStart,
+                                                                        IMG_UINT32 ui32PageNumOffset,
+                                                                        IMG_UINT32 ui32PageNum,
+                                                                        unsigned long *pulStart)
 {
        IMG_SYS_PHYADDR SysPAddr;
        IMG_CPU_PHYADDR CpuPAddr;
        SysPAddr = psLinuxMemArea->uData.sExternalKV.uPhysAddr.pSysPhysAddr[ui32PageNumOffset + ui32PageNum];
        CpuPAddr = SysSysPAddrToCpuPAddr(SysPAddr);
-       return CpuPAddr.uiAddr;
+       *pulStart = CpuPAddr.uiAddr;
+       return IMG_TRUE;
 }
 
-static unsigned long AllocPagesAreaToPhys(LinuxMemArea *psLinuxMemArea,
-                                                                                 IMG_VOID *pvRangeAddrStart,
-                                                                                 IMG_UINT32 ui32PageNumOffset,
-                                                                                 IMG_UINT32 ui32PageNum)
+static IMG_BOOL AllocPagesAreaToPhys(LinuxMemArea *psLinuxMemArea,
+                                                                        IMG_VOID *pvRangeAddrStart,
+                                                                        IMG_UINT32 ui32PageNumOffset,
+                                                                        IMG_UINT32 ui32PageNum,
+                                                                        unsigned long *pulStart)
 {
        struct page *pPage;
-       pPage = psLinuxMemArea->uData.sPageList.pvPageList[ui32PageNumOffset + ui32PageNum];
-       return page_to_pfn(pPage) << PAGE_SHIFT;
+
+       pPage = psLinuxMemArea->uData.sPageList.ppsPageList[ui32PageNumOffset + ui32PageNum];
+       *pulStart = page_to_pfn(pPage) << PAGE_SHIFT;
+       return IMG_TRUE;
+}
+
+static IMG_BOOL AllocPagesSparseAreaToPhys(LinuxMemArea *psLinuxMemArea,
+                                                                                  IMG_VOID *pvRangeAddrStart,
+                                                                                  IMG_UINT32 ui32PageNumOffset,
+                                                                                  IMG_UINT32 ui32PageNum,
+                                                                                  unsigned long *pulStart)
+{
+       IMG_UINT32 ui32VirtOffset = (ui32PageNumOffset + ui32PageNum) << PAGE_SHIFT;
+       IMG_UINT32 ui32PhysOffset;
+       struct page *pPage;
+
+       if (BM_VirtOffsetToPhysical(psLinuxMemArea->hBMHandle, ui32VirtOffset, &ui32PhysOffset))
+       {
+               PVR_ASSERT(ui32PhysOffset <= ui32VirtOffset);
+               pPage = psLinuxMemArea->uData.sPageList.ppsPageList[ui32PhysOffset >> PAGE_SHIFT];
+               *pulStart = page_to_pfn(pPage) << PAGE_SHIFT;
+               return IMG_TRUE;
+       }
+
+       return IMG_FALSE;
 }
 
-#endif 
 
-#ifndef __mips__
+static IMG_BOOL IONAreaToPhys(LinuxMemArea *psLinuxMemArea,
+                                                         IMG_VOID *pvRangeAddrStart,
+                                                         IMG_UINT32 ui32PageNumOffset,
+                                                         IMG_UINT32 ui32PageNum,
+                                                         unsigned long *pulStart)
+{
+       IMG_CPU_PHYADDR CpuPAddr;
+       CpuPAddr = psLinuxMemArea->uData.sIONTilerAlloc.pCPUPhysAddrs[ui32PageNumOffset + ui32PageNum];
+       *pulStart = CpuPAddr.uiAddr;
+       return IMG_TRUE;
+}
+
+#endif /* defined(CONFIG_OUTER_CACHE) */
+
+/* g_sMMapMutex must be held while this function is called */
+
 static
 IMG_VOID *FindMMapBaseVAddr(struct list_head *psMMapOffsetStructList,
                                                        IMG_VOID *pvRangeAddrStart, IMG_UINT32 ui32Length)
@@ -2698,7 +3925,10 @@ IMG_VOID *FindMMapBaseVAddr(struct list_head *psMMapOffsetStructList,
        PKV_OFFSET_STRUCT psOffsetStruct;
        IMG_VOID *pvMinVAddr;
 
-       
+       /* There's no kernel-virtual for this type of allocation, so if
+        * we're flushing it, it must be user-virtual, and therefore
+        * have a mapping.
+        */
        list_for_each_entry(psOffsetStruct, psMMapOffsetStructList, sAreaItem)
        {
                if(OSGetCurrentProcessIDKM() != psOffsetStruct->ui32PID)
@@ -2706,7 +3936,7 @@ IMG_VOID *FindMMapBaseVAddr(struct list_head *psMMapOffsetStructList,
 
                pvMinVAddr = (IMG_VOID *)psOffsetStruct->ui32UserVAddr;
 
-               
+               /* Within permissible range */
                if(pvRangeAddrStart >= pvMinVAddr &&
                   ui32Length <= psOffsetStruct->ui32RealByteSize)
                        return pvMinVAddr;
@@ -2715,8 +3945,42 @@ IMG_VOID *FindMMapBaseVAddr(struct list_head *psMMapOffsetStructList,
        return IMG_NULL;
 }
 
+extern PVRSRV_LINUX_MUTEX g_sMMapMutex;
+
+static inline void DoInnerCacheOp(IMG_HANDLE hOSMemHandle,
+                                                                 IMG_UINT32 ui32ByteOffset,
+                                                                 IMG_VOID *pvRangeAddrStart,
+                                                                 IMG_UINT32 ui32Length,
+                                                                 InnerCacheOp_t pfnInnerCacheOp)
+{
+       LinuxMemArea *psLinuxMemArea = hOSMemHandle;
+
+       if (!psLinuxMemArea->hBMHandle)
+       {
+               pfnInnerCacheOp(pvRangeAddrStart, pvRangeAddrStart + ui32Length);
+       }
+       else
+       {
+               IMG_UINT32 ui32ByteRemain = ui32Length;
+               IMG_UINT32 ui32BytesToDo = PAGE_SIZE - (((IMG_UINT32) pvRangeAddrStart) & (~PAGE_MASK));
+               IMG_UINT8 *pbDo = (IMG_UINT8 *) pvRangeAddrStart;
+       
+               while(ui32ByteRemain)
+               {
+                       if (BM_MapPageAtOffset(psLinuxMemArea->hBMHandle, ui32ByteOffset + (ui32Length - ui32ByteRemain)))
+                       {
+                               pfnInnerCacheOp(pbDo, pbDo + ui32BytesToDo);
+                       }
+                       pbDo += ui32BytesToDo;
+                       ui32ByteRemain -= ui32BytesToDo;
+                       ui32BytesToDo = MIN(ui32ByteRemain, PAGE_SIZE);
+               }
+       }
+}
+
 static
 IMG_BOOL CheckExecuteCacheOp(IMG_HANDLE hOSMemHandle,
+                                                        IMG_UINT32 ui32ByteOffset,
                                                         IMG_VOID *pvRangeAddrStart,
                                                         IMG_UINT32 ui32Length,
                                                         InnerCacheOp_t pfnInnerCacheOp,
@@ -2734,8 +3998,10 @@ IMG_BOOL CheckExecuteCacheOp(IMG_HANDLE hOSMemHandle,
 
        PVR_ASSERT(psLinuxMemArea != IMG_NULL);
 
-       ui32AreaLength = psLinuxMemArea->ui32ByteSize;
+       LinuxLockMutex(&g_sMMapMutex);
+
        psMMapOffsetStructList = &psLinuxMemArea->sMMapOffsetStructList;
+       ui32AreaLength = psLinuxMemArea->ui32ByteSize;
 
        PVR_ASSERT(ui32Length <= ui32AreaLength);
 
@@ -2745,7 +4011,7 @@ IMG_BOOL CheckExecuteCacheOp(IMG_HANDLE hOSMemHandle,
                psLinuxMemArea = psLinuxMemArea->uData.sSubAlloc.psParentLinuxMemArea;
        }
 
-       
+       /* Recursion surely isn't possible? */
        PVR_ASSERT(psLinuxMemArea->eAreaType != LINUX_MEM_AREA_SUB_ALLOC);
 
        switch(psLinuxMemArea->eAreaType)
@@ -2756,63 +4022,84 @@ IMG_BOOL CheckExecuteCacheOp(IMG_HANDLE hOSMemHandle,
                        {
                                pvMinVAddr = psLinuxMemArea->uData.sVmalloc.pvVmallocAddress + ui32AreaOffset;
 
-                               
+                               /* Outside permissible range */
                                if(pvRangeAddrStart < pvMinVAddr)
                                        goto err_blocked;
 
-                               pfnInnerCacheOp(pvRangeAddrStart, pvRangeAddrStart + ui32Length);
+                               DoInnerCacheOp(hOSMemHandle,
+                                                          ui32ByteOffset,
+                                                          pvRangeAddrStart,
+                                                          ui32Length,
+                                                          pfnInnerCacheOp);
                        }
                        else
                        {
-                               
-                               
+                               /* If this isn't a vmalloc address, assume we're flushing by
+                                * user-virtual. Compute the mmap base vaddr and use this to
+                                * compute the offset in vmalloc space.
+                                */
 
                                pvMinVAddr = FindMMapBaseVAddr(psMMapOffsetStructList,
                                                                                           pvRangeAddrStart, ui32Length);
                                if(!pvMinVAddr)
                                        goto err_blocked;
 
-                               pfnInnerCacheOp(pvRangeAddrStart, pvRangeAddrStart + ui32Length);
+                               DoInnerCacheOp(hOSMemHandle,
+                                                          ui32ByteOffset,
+                                                          pvRangeAddrStart,
+                                                          ui32Length,
+                                                          pfnInnerCacheOp);
 
 #if defined(CONFIG_OUTER_CACHE)
-                               
+                               /*
+                                * We don't need to worry about cache aliasing here because
+                                * we have already flushed the virtually-indexed caches (L1
+                                * etc.) by the supplied user-virtual addresses.
+                                *
+                                * The vmalloc address will only be used to determine
+                                * affected physical pages for outer cache flushing.
+                                */
                                pvRangeAddrStart = psLinuxMemArea->uData.sVmalloc.pvVmallocAddress +
                                                                   (ui32AreaOffset & PAGE_MASK) + (pvRangeAddrStart - pvMinVAddr);
                        }
 
                        pfnMemAreaToPhys = VMallocAreaToPhys;
-#else 
+#else /* defined(CONFIG_OUTER_CACHE) */
                        }
-#endif 
+#endif /* defined(CONFIG_OUTER_CACHE) */
                        break;
                }
 
                case LINUX_MEM_AREA_EXTERNAL_KV:
                {
-                       
+                       /* We'll only see bPhysContig for frame buffers, and we shouldn't
+                        * be flushing those (they're write combined or uncached).
+                        */
                        if (psLinuxMemArea->uData.sExternalKV.bPhysContig == IMG_TRUE)
                        {
                                PVR_DPF((PVR_DBG_WARNING, "%s: Attempt to flush contiguous external memory", __func__));
-
                                goto err_blocked;
                        }
 
-                       
+                       /* If it has a kernel virtual address, something odd has happened.
+                        * We expect EXTERNAL_KV _only_ from the wrapping of ALLOC_PAGES.
+                        */
                        if (psLinuxMemArea->uData.sExternalKV.pvExternalKV != IMG_NULL)
                        {
                                PVR_DPF((PVR_DBG_WARNING, "%s: Attempt to flush external memory with a kernel virtual address", __func__));
-
                                goto err_blocked;
                        }
 
-                       
-
                        pvMinVAddr = FindMMapBaseVAddr(psMMapOffsetStructList,
                                                                                   pvRangeAddrStart, ui32Length);
                        if(!pvMinVAddr)
                                goto err_blocked;
 
-                       pfnInnerCacheOp(pvRangeAddrStart, pvRangeAddrStart + ui32Length);
+                       DoInnerCacheOp(hOSMemHandle,
+                                                  ui32ByteOffset,
+                                                  pvRangeAddrStart,
+                                                  ui32Length,
+                                                  pfnInnerCacheOp);
 
 #if defined(CONFIG_OUTER_CACHE)
                        ui32PageNumOffset = ((ui32AreaOffset & PAGE_MASK) + (pvRangeAddrStart - pvMinVAddr)) >> PAGE_SHIFT;
@@ -2821,6 +4108,26 @@ IMG_BOOL CheckExecuteCacheOp(IMG_HANDLE hOSMemHandle,
                        break;
                }
 
+               case LINUX_MEM_AREA_ION:
+               {
+                       pvMinVAddr = FindMMapBaseVAddr(psMMapOffsetStructList,
+                                                                                  pvRangeAddrStart, ui32Length);
+                       if(!pvMinVAddr)
+                               goto err_blocked;
+
+                       DoInnerCacheOp(hOSMemHandle,
+                                                  ui32ByteOffset,
+                                                  pvRangeAddrStart,
+                                                  ui32Length,
+                                                  pfnInnerCacheOp);
+
+#if defined(CONFIG_OUTER_CACHE)
+                       ui32PageNumOffset = ((ui32AreaOffset & PAGE_MASK) + (pvRangeAddrStart - pvMinVAddr)) >> PAGE_SHIFT;
+                       pfnMemAreaToPhys = IONAreaToPhys;
+#endif
+                       break;
+               }
+
                case LINUX_MEM_AREA_ALLOC_PAGES:
                {
                        pvMinVAddr = FindMMapBaseVAddr(psMMapOffsetStructList,
@@ -2828,11 +4135,22 @@ IMG_BOOL CheckExecuteCacheOp(IMG_HANDLE hOSMemHandle,
                        if(!pvMinVAddr)
                                goto err_blocked;
 
-                       pfnInnerCacheOp(pvRangeAddrStart, pvRangeAddrStart + ui32Length);
+                       DoInnerCacheOp(hOSMemHandle,
+                                                  ui32ByteOffset,
+                                                  pvRangeAddrStart,
+                                                  ui32Length,
+                                                  pfnInnerCacheOp);
 
 #if defined(CONFIG_OUTER_CACHE)
                        ui32PageNumOffset = ((ui32AreaOffset & PAGE_MASK) + (pvRangeAddrStart - pvMinVAddr)) >> PAGE_SHIFT;
-                       pfnMemAreaToPhys = AllocPagesAreaToPhys;
+                       if (psLinuxMemArea->hBMHandle)
+                       {
+                               pfnMemAreaToPhys = AllocPagesSparseAreaToPhys;
+                       }
+                       else
+                       {
+                               pfnMemAreaToPhys = AllocPagesAreaToPhys;
+                       }
 #endif
                        break;
                }
@@ -2841,35 +4159,41 @@ IMG_BOOL CheckExecuteCacheOp(IMG_HANDLE hOSMemHandle,
                        PVR_DBG_BREAK;
        }
 
+       LinuxUnLockMutex(&g_sMMapMutex);
+
 #if defined(CONFIG_OUTER_CACHE)
        PVR_ASSERT(pfnMemAreaToPhys != IMG_NULL);
 
-       
+       /* Outer caches need some more work, to get a list of physical addresses */
        {
                unsigned long ulStart, ulEnd, ulLength, ulStartOffset, ulEndOffset;
                IMG_UINT32 i, ui32NumPages;
+               IMG_BOOL bValidPage;
 
-               
+               /* Length and offsets of flush region WRT page alignment */
                ulLength = (unsigned long)ui32Length;
                ulStartOffset = ((unsigned long)pvRangeAddrStart) & (PAGE_SIZE - 1);
                ulEndOffset = ((unsigned long)pvRangeAddrStart + ulLength) & (PAGE_SIZE - 1);
 
-               
+               /* The affected pages, rounded up */
                ui32NumPages = (ulStartOffset + ulLength + PAGE_SIZE - 1) >> PAGE_SHIFT;
 
                for(i = 0; i < ui32NumPages; i++)
                {
-                       ulStart = pfnMemAreaToPhys(psLinuxMemArea, pvRangeAddrStart,
-                                                                          ui32PageNumOffset, i);
-                       ulEnd = ulStart + PAGE_SIZE;
-
-                       if(i == ui32NumPages - 1 && ulEndOffset != 0)
-                               ulEnd = ulStart + ulEndOffset;
-
-                       if(i == 0)
-                               ulStart += ulStartOffset;
-
-                       pfnOuterCacheOp(ulStart, ulEnd);
+                       bValidPage = pfnMemAreaToPhys(psLinuxMemArea, pvRangeAddrStart,
+                                                                          ui32PageNumOffset, i, &ulStart);
+                       if (bValidPage)
+                       {
+                               ulEnd = ulStart + PAGE_SIZE;
+       
+                               if(i == ui32NumPages - 1 && ulEndOffset != 0)
+                                       ulEnd = ulStart + ulEndOffset;
+       
+                               if(i == 0)
+                                       ulStart += ulStartOffset;
+       
+                               pfnOuterCacheOp(ulStart, ulEnd);
+                       }
                }
        }
 #endif
@@ -2881,11 +4205,10 @@ err_blocked:
                                                          "%p-%p (type %d)", __func__,
                         pvRangeAddrStart, pvRangeAddrStart + ui32Length,
                         psLinuxMemArea->eAreaType));
+       LinuxUnLockMutex(&g_sMMapMutex);
        return IMG_FALSE;
 }
 
-#endif
-
 #if defined(__i386__)
 
 #define ROUND_UP(x,a) (((x) + (a) - 1) & ~((a) - 1))
@@ -2907,13 +4230,15 @@ static void x86_flush_cache_range(const void *pvStart, const void *pvEnd)
 
        mb();
        for(pbBase = pbStart; pbBase < pbEnd; pbBase += boot_cpu_data.x86_clflush_size)
+       {
                clflush(pbBase);
+       }
        mb();
 }
 
 IMG_VOID OSCleanCPUCacheKM(IMG_VOID)
 {
-       
+       /* No clean feature on x86 */
        ON_EACH_CPU(per_cpu_cache_flush, NULL, 1);
 }
 
@@ -2923,33 +4248,36 @@ IMG_VOID OSFlushCPUCacheKM(IMG_VOID)
 }
 
 IMG_BOOL OSFlushCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                               IMG_UINT32 ui32ByteOffset,
                                                                IMG_VOID *pvRangeAddrStart,
                                                                IMG_UINT32 ui32Length)
 {
-       
-       return CheckExecuteCacheOp(hOSMemHandle, pvRangeAddrStart, ui32Length,
+       /* Write-back and invalidate */
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset, pvRangeAddrStart, ui32Length,
                                                           x86_flush_cache_range, IMG_NULL);
 }
 
 IMG_BOOL OSCleanCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                               IMG_UINT32 ui32ByteOffset,
                                                                IMG_VOID *pvRangeAddrStart,
                                                                IMG_UINT32 ui32Length)
 {
-       
-       return CheckExecuteCacheOp(hOSMemHandle, pvRangeAddrStart, ui32Length,
+       /* No clean feature on x86 */
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset, pvRangeAddrStart, ui32Length,
                                                           x86_flush_cache_range, IMG_NULL);
 }
 
 IMG_BOOL OSInvalidateCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                                        IMG_UINT32 ui32ByteOffset,
                                                                         IMG_VOID *pvRangeAddrStart,
                                                                         IMG_UINT32 ui32Length)
 {
-       
-       return CheckExecuteCacheOp(hOSMemHandle, pvRangeAddrStart, ui32Length,
+       /* No invalidate-only support */
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset, pvRangeAddrStart, ui32Length,
                                                           x86_flush_cache_range, IMG_NULL);
 }
 
-#else 
+#else /* defined(__i386__) */
 
 #if defined(__arm__)
 
@@ -2961,25 +4289,35 @@ static void per_cpu_cache_flush(void *arg)
 
 IMG_VOID OSCleanCPUCacheKM(IMG_VOID)
 {
-       
+       /* No full (inner) cache clean op */
        ON_EACH_CPU(per_cpu_cache_flush, NULL, 1);
-#if defined(CONFIG_OUTER_CACHE) && !defined(PVR_NO_FULL_CACHE_OPS)
-       outer_clean_all();
+#if defined(CONFIG_OUTER_CACHE)
+       outer_clean_range(0, ULONG_MAX);
 #endif
 }
 
 IMG_VOID OSFlushCPUCacheKM(IMG_VOID)
 {
        ON_EACH_CPU(per_cpu_cache_flush, NULL, 1);
-#if defined(CONFIG_OUTER_CACHE) && !defined(PVR_NO_FULL_CACHE_OPS)
+#if defined(CONFIG_OUTER_CACHE) && \
+       (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37))
+       /* To use the "deferred flush" (not clean) DDK feature you need a kernel
+        * implementation of outer_flush_all() for ARM CPUs with an outer cache
+        * controller (e.g. PL310, common with Cortex A9 and later).
+        *
+        * Reference DDKs don't require this functionality, as they will only
+        * clean the cache, never flush (clean+invalidate) it.
+        */
        outer_flush_all();
 #endif
 }
 
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,34))
 static inline size_t pvr_dmac_range_len(const void *pvStart, const void *pvEnd)
 {
        return (size_t)((char *)pvEnd - (char *)pvStart);
 }
+#endif
 
 static void pvr_dmac_inv_range(const void *pvStart, const void *pvEnd)
 {
@@ -3000,81 +4338,235 @@ static void pvr_dmac_clean_range(const void *pvStart, const void *pvEnd)
 }
 
 IMG_BOOL OSFlushCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                               IMG_UINT32 ui32ByteOffset,
                                                                IMG_VOID *pvRangeAddrStart,
                                                                IMG_UINT32 ui32Length)
 {
-       return CheckExecuteCacheOp(hOSMemHandle, pvRangeAddrStart, ui32Length,
-                                                          dmac_flush_range, (OuterCacheOp_t)outer_flush_range);
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset,
+                                                          pvRangeAddrStart, ui32Length,
+                                                          dmac_flush_range, outer_flush_range);
 }
 
 IMG_BOOL OSCleanCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                               IMG_UINT32 ui32ByteOffset,
                                                                IMG_VOID *pvRangeAddrStart,
                                                                IMG_UINT32 ui32Length)
 {
-       return CheckExecuteCacheOp(hOSMemHandle, pvRangeAddrStart, ui32Length,
-                                                          pvr_dmac_clean_range, (OuterCacheOp_t)outer_clean_range);
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset,
+                                                          pvRangeAddrStart, ui32Length,
+                                                          pvr_dmac_clean_range, outer_clean_range);
 }
 
 IMG_BOOL OSInvalidateCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                                        IMG_UINT32 ui32ByteOffset,
                                                                         IMG_VOID *pvRangeAddrStart,
                                                                         IMG_UINT32 ui32Length)
 {
-       return CheckExecuteCacheOp(hOSMemHandle, pvRangeAddrStart, ui32Length,
-                                                          pvr_dmac_inv_range, (OuterCacheOp_t)outer_inv_range);
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset,
+                                                          pvRangeAddrStart, ui32Length,
+                                                          pvr_dmac_inv_range, outer_inv_range);
 }
 
-#else 
+#else /* defined(__arm__) */
 
 #if defined(__mips__)
+/* 
+ * dmac cache functions are supposed to be used for dma 
+ * memory which comes from dma-able memory. However examining
+ * the implementation of dmac cache functions and experimenting,
+ * can assert that dmac functions are safe to use for high-mem
+ * memory as well for our OS{Clean/Flush/Invalidate}Cache functions
+ * 
+ */
+
 IMG_VOID OSCleanCPUCacheKM(IMG_VOID)
 {
-       
+       /* dmac functions flush full cache if size is larger than
+        * p-cache size. This is a workaround for the fact that
+        * __flush_cache_all is not an exported symbol. Please
+        * replace with custom function if available in latest
+        * version of linux being used.
+        * Arbitrary large number (1MB) which should be larger than 
+        * mips p-cache sizes for some time in future.
+        * */
        dma_cache_wback(0, 0x100000);
 }
 
 IMG_VOID OSFlushCPUCacheKM(IMG_VOID)
 {
-       
+       /* dmac functions flush full cache if size is larger than
+        * p-cache size. This is a workaround for the fact that
+        * __flush_cache_all is not an exported symbol. Please
+        * replace with custom function if available in latest
+        * version of linux being used.
+        * Arbitrary large number (1MB) which should be larger than 
+        * mips p-cache sizes for some time in future.
+        * */
        dma_cache_wback_inv(0, 0x100000);
 }
 
+static inline IMG_UINT32 pvr_dma_range_len(const void *pvStart, const void *pvEnd)
+{
+       return (IMG_UINT32)((char *)pvEnd - (char *)pvStart);
+}
+
+static void pvr_dma_cache_wback_inv(const void *pvStart, const void *pvEnd)
+{
+       dma_cache_wback_inv((IMG_UINTPTR_T)pvStart, pvr_dma_range_len(pvStart, pvEnd)); 
+}
+
+static void pvr_dma_cache_wback(const void *pvStart, const void *pvEnd)
+{
+       dma_cache_wback((IMG_UINTPTR_T)pvStart, pvr_dma_range_len(pvStart, pvEnd));
+}
+
+static void pvr_dma_cache_inv(const void *pvStart, const void *pvEnd)
+{
+       dma_cache_inv((IMG_UINTPTR_T)pvStart, pvr_dma_range_len(pvStart, pvEnd));
+}
+
 IMG_BOOL OSFlushCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                               IMG_UINT32 ui32ByteOffset,
                                                                IMG_VOID *pvRangeAddrStart,
                                                                IMG_UINT32 ui32Length)
 {
-       if (ui32Length)
-               dma_cache_wback_inv((IMG_UINTPTR_T)pvRangeAddrStart, ui32Length);       
-       return IMG_TRUE;
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset,
+                                                          pvRangeAddrStart, ui32Length,
+                                                          pvr_dma_cache_wback_inv, IMG_NULL);
 }
 
 IMG_BOOL OSCleanCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                               IMG_UINT32 ui32ByteOffset,
                                                                IMG_VOID *pvRangeAddrStart,
                                                                IMG_UINT32 ui32Length)
 {
-       if (ui32Length)
-               dma_cache_wback((IMG_UINTPTR_T)pvRangeAddrStart, ui32Length);
-       return IMG_TRUE;
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset,
+                                                          pvRangeAddrStart, ui32Length,
+                                                          pvr_dma_cache_wback, IMG_NULL);
 }
 
 IMG_BOOL OSInvalidateCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                                        IMG_UINT32 ui32ByteOffset,
                                                                         IMG_VOID *pvRangeAddrStart,
                                                                         IMG_UINT32 ui32Length)
 {
-       if (ui32Length)
-               dma_cache_inv((IMG_UINTPTR_T)pvRangeAddrStart, ui32Length);
-       return IMG_TRUE;
+       return CheckExecuteCacheOp(hOSMemHandle, ui32ByteOffset,
+                                                          pvRangeAddrStart, ui32Length,
+                                                          pvr_dma_cache_inv, IMG_NULL);
 }
 
-#else 
+#else /* defined(__mips__) */
 
 #error "Implement CPU cache flush/clean/invalidate primitives for this CPU!"
 
-#endif 
+#endif /* defined(__mips__) */
+
+#endif /* defined(__arm__) */
 
-#endif 
+#endif /* defined(__i386__) */
 
-#endif 
+typedef struct _AtomicStruct
+{
+       atomic_t RefCount;
+} AtomicStruct;
+
+PVRSRV_ERROR OSAtomicAlloc(IMG_PVOID *ppvRefCount)
+{
+       AtomicStruct *psRefCount;
 
+       psRefCount = kmalloc(sizeof(AtomicStruct), GFP_KERNEL);
+       if (psRefCount == NULL)
+       {
+               return PVRSRV_ERROR_OUT_OF_MEMORY;
+       }
+       atomic_set(&psRefCount->RefCount, 0);
+       
+       *ppvRefCount = psRefCount;
+       return PVRSRV_OK;
+}
+
+IMG_VOID OSAtomicFree(IMG_PVOID pvRefCount)
+{
+       AtomicStruct *psRefCount = pvRefCount;
+
+       PVR_ASSERT(atomic_read(&psRefCount->RefCount) == 0);
+       kfree(psRefCount);
+}
+
+IMG_VOID OSAtomicInc(IMG_PVOID pvRefCount)
+{
+       AtomicStruct *psRefCount = pvRefCount;
+
+       atomic_inc(&psRefCount->RefCount);
+}
+
+IMG_BOOL OSAtomicDecAndTest(IMG_PVOID pvRefCount)
+{
+       AtomicStruct *psRefCount = pvRefCount;
+
+       return atomic_dec_and_test(&psRefCount->RefCount) ? IMG_TRUE:IMG_FALSE;
+}
+
+IMG_UINT32 OSAtomicRead(IMG_PVOID pvRefCount)
+{
+       AtomicStruct *psRefCount = pvRefCount;
+
+       return (IMG_UINT32) atomic_read(&psRefCount->RefCount);
+}
+
+IMG_VOID OSReleaseBridgeLock(IMG_VOID)
+{
+       LinuxUnLockMutex(&gPVRSRVLock);
+}
+
+IMG_VOID OSReacquireBridgeLock(IMG_VOID)
+{
+       LinuxLockMutex(&gPVRSRVLock);
+}
+
+typedef struct _OSTime
+{
+       unsigned long ulTime;
+} OSTime;
+
+PVRSRV_ERROR OSTimeCreateWithUSOffset(IMG_PVOID *pvRet, IMG_UINT32 ui32USOffset)
+{
+       OSTime *psOSTime;
+
+       psOSTime = kmalloc(sizeof(OSTime), GFP_KERNEL);
+       if (psOSTime == IMG_NULL)
+       {
+               return PVRSRV_ERROR_OUT_OF_MEMORY;
+       }
+
+       psOSTime->ulTime = usecs_to_jiffies(jiffies_to_usecs(jiffies) + ui32USOffset);
+       *pvRet = psOSTime;
+       return PVRSRV_OK;
+}
+
+
+IMG_BOOL OSTimeHasTimePassed(IMG_PVOID pvData)
+{
+       OSTime *psOSTime = pvData;
+
+       if (time_is_before_jiffies(psOSTime->ulTime))
+       {
+               return IMG_TRUE;
+       }
+       return IMG_FALSE;
+}
+
+IMG_VOID OSTimeDestroy(IMG_PVOID pvData)
+{
+       kfree(pvData);
+}
+
+IMG_VOID OSGetCurrentProcessNameKM(IMG_CHAR *pszName, IMG_UINT32 ui32Size)
+{
+       strncpy(pszName, current->comm, MIN(ui32Size,TASK_COMM_LEN));
+}
+
+/* One time osfunc initialisation */
 PVRSRV_ERROR PVROSFuncInit(IMG_VOID)
 {
 #if defined(PVR_LINUX_TIMERS_USING_WORKQUEUES)
@@ -3101,11 +4593,30 @@ PVRSRV_ERROR PVROSFuncInit(IMG_VOID)
         }
     }
 #endif
+
+#if defined (SUPPORT_ION)
+       {
+               PVRSRV_ERROR eError;
+
+               eError = IonInit();
+               if (eError != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "%s: IonInit failed", __FUNCTION__));
+               }
+       }
+#endif
     return PVRSRV_OK;
 }
 
+/*
+ * Osfunc deinitialisation.
+ * Note that PVROSFuncInit may not have been called
+ */
 IMG_VOID PVROSFuncDeInit(IMG_VOID)
 {
+#if defined (SUPPORT_ION)
+       IonDeinit();
+#endif
 #if defined(PVR_LINUX_TIMERS_USING_WORKQUEUES)
     if (psTimerWorkQueue != NULL)
     {
index 6b57dfc..a22b461 100644 (file)
@@ -1,35 +1,54 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux specific per process data functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "services_headers.h"
 #include "osperproc.h"
 
 #include "env_perproc.h"
 #include "proc.h"
+#if defined (SUPPORT_ION)
+#include "linux/ion.h"
 
+extern struct ion_device *psIonDev;
+#endif
 extern IMG_UINT32 gui32ReleasePID;
 
 PVRSRV_ERROR OSPerProcessPrivateDataInit(IMG_HANDLE *phOsPrivateData)
@@ -57,14 +76,28 @@ PVRSRV_ERROR OSPerProcessPrivateDataInit(IMG_HANDLE *phOsPrivateData)
 
        psEnvPerProc->hBlockAlloc = hBlockAlloc;
 
-       
+       /* Linux specific mmap processing */
        LinuxMMapPerProcessConnect(psEnvPerProc);
 
 #if defined(SUPPORT_DRI_DRM) && defined(PVR_SECURE_DRM_AUTH_EXPORT)
-       
+       /* Linked list of PVRSRV_FILE_PRIVATE_DATA structures */
        INIT_LIST_HEAD(&psEnvPerProc->sDRMAuthListHead);
 #endif
-
+#if defined(SUPPORT_ION)
+       OSSNPrintf(psEnvPerProc->azIonClientName, ION_CLIENT_NAME_SIZE, "pvr_ion_client-%d", OSGetCurrentProcessIDKM());
+       psEnvPerProc->psIONClient =
+               ion_client_create(psIonDev,
+                                                 1 << ION_HEAP_TYPE_SYSTEM_CONTIG |
+                                                 1 << ION_HEAP_TYPE_SYSTEM,
+                                                 psEnvPerProc->azIonClientName);
+       if (IS_ERR_OR_NULL(psEnvPerProc->psIONClient))
+       {
+               PVR_DPF((PVR_DBG_ERROR, "OSPerProcessPrivateDataInit: Couldn't create "
+                                                               "ion client for per process data"));
+               return PVRSRV_ERROR_OUT_OF_MEMORY;
+       }
+#endif /* SUPPORT_ION */
        return PVRSRV_OK;
 }
 
@@ -80,17 +113,17 @@ PVRSRV_ERROR OSPerProcessPrivateDataDeInit(IMG_HANDLE hOsPrivateData)
 
        psEnvPerProc = (PVRSRV_ENV_PER_PROCESS_DATA *)hOsPrivateData;
 
-       
+       /* Linux specific mmap processing */
        LinuxMMapPerProcessDisconnect(psEnvPerProc);
 
-       
+       /* Remove per process /proc entries */
        RemovePerProcessProcDir(psEnvPerProc);
 
        eError = OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
                                sizeof(PVRSRV_ENV_PER_PROCESS_DATA),
                                hOsPrivateData,
                                psEnvPerProc->hBlockAlloc);
-       
+       /*not nulling pointer, copy on stack*/
 
        if (eError != PVRSRV_OK)
        {
index 13d9b0d..0124737 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Parameter dump macro target routines
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if defined (SUPPORT_SGX) || defined (SUPPORT_VGX)
 #if defined (PDUMP)
@@ -30,7 +45,7 @@
 #include <asm/atomic.h>
 #include <stdarg.h>
 #if defined (SUPPORT_SGX)
-#include "sgxdefs.h" 
+#include "sgxdefs.h" /* Is this still needed? */
 #endif
 #include "services_headers.h"
 
 
 #include "dbgdrvif.h"
 #if defined (SUPPORT_SGX)
-#include "sgxmmu.h"
+#include "sgxmmu.h"/* Is this still needed? */
 #endif
 #include "mm.h"
 #include "pdump_km.h"
 #include "pdump_int.h"
 
-#include <linux/kernel.h> 
-#include <linux/string.h> 
+#include <linux/kernel.h> // sprintf
+#include <linux/string.h> // strncpy, strlen
 
 static IMG_BOOL PDumpWriteString2              (IMG_CHAR * pszString, IMG_UINT32 ui32Flags);
 static IMG_BOOL PDumpWriteILock                        (PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_UINT32 ui32Count, IMG_UINT32 ui32Flags);
@@ -56,6 +71,9 @@ static IMG_VOID DbgSetMarker                  (PDBG_STREAM psStream, IMG_UINT32 ui32Marker);
 #define PDUMP_DATAMASTER_PIXEL         (1)
 #define PDUMP_DATAMASTER_EDM           (3)
 
+/*
+       Maximum file size to split output files
+*/
 #define MAX_FILE_SIZE  0x40000000
 
 static atomic_t gsPDumpSuspended = ATOMIC_INIT(0);
@@ -87,13 +105,14 @@ static PDBG_PDUMP_STATE gsDBGPdumpState = {{IMG_NULL}, 0, IMG_NULL, IMG_NULL, IM
 
 
 
-IMG_VOID DBGDrvGetServiceTable(IMG_VOID **fn_table);
-
 static inline IMG_BOOL PDumpSuspended(IMG_VOID)
 {
        return (atomic_read(&gsPDumpSuspended) != 0) ? IMG_TRUE : IMG_FALSE;
 }
 
+/*!
+ * \name       PDumpOSGetScriptString
+ */
 PVRSRV_ERROR PDumpOSGetScriptString(IMG_HANDLE *phScript,
                                                                        IMG_UINT32 *pui32MaxLen)
 {
@@ -106,6 +125,9 @@ PVRSRV_ERROR PDumpOSGetScriptString(IMG_HANDLE *phScript,
        return PVRSRV_OK;
 }
 
+/*!
+ * \name       PDumpOSGetMessageString
+ */
 PVRSRV_ERROR PDumpOSGetMessageString(IMG_CHAR **ppszMsg,
                                                                         IMG_UINT32 *pui32MaxLen)
 {
@@ -118,6 +140,9 @@ PVRSRV_ERROR PDumpOSGetMessageString(IMG_CHAR **ppszMsg,
        return PVRSRV_OK;
 }
 
+/*!
+ * \name       PDumpOSGetFilenameString
+ */
 PVRSRV_ERROR PDumpOSGetFilenameString(IMG_CHAR **ppszFile,
                                                                         IMG_UINT32 *pui32MaxLen)
 {
@@ -130,11 +155,17 @@ PVRSRV_ERROR PDumpOSGetFilenameString(IMG_CHAR **ppszFile,
        return PVRSRV_OK;
 }
 
+/*!
+ * \name       PDumpOSWriteString2
+ */
 IMG_BOOL PDumpOSWriteString2(IMG_HANDLE hScript, IMG_UINT32 ui32Flags)
 {
        return PDumpWriteString2(hScript, ui32Flags);
 }
 
+/*!
+ * \name       PDumpOSBufprintf
+ */
 PVRSRV_ERROR PDumpOSBufprintf(IMG_HANDLE hBuf, IMG_UINT32 ui32ScriptSizeMax, IMG_CHAR* pszFormat, ...)
 {
        IMG_CHAR* pszBuf = hBuf;
@@ -147,7 +178,7 @@ PVRSRV_ERROR PDumpOSBufprintf(IMG_HANDLE hBuf, IMG_UINT32 ui32ScriptSizeMax, IMG
 
        va_end(vaArgs);
 
-       if (n>=(IMG_INT32)ui32ScriptSizeMax || n==-1)   
+       if (n>=(IMG_INT32)ui32ScriptSizeMax || n==-1)   /* glibc >= 2.1 or glibc 2.0 */
        {
                PVR_DPF((PVR_DBG_ERROR, "Buffer overflow detected, pdump output may be incomplete."));
 
@@ -160,13 +191,16 @@ PVRSRV_ERROR PDumpOSBufprintf(IMG_HANDLE hBuf, IMG_UINT32 ui32ScriptSizeMax, IMG
        return PVRSRV_OK;
 }
 
+/*!
+ * \name       PDumpOSVSprintf
+ */
 PVRSRV_ERROR PDumpOSVSprintf(IMG_CHAR *pszComment, IMG_UINT32 ui32ScriptSizeMax, IMG_CHAR* pszFormat, PDUMP_va_list vaArgs)
 {
        IMG_INT32 n;
 
        n = vsnprintf(pszComment, ui32ScriptSizeMax, pszFormat, vaArgs);
 
-       if (n>=(IMG_INT32)ui32ScriptSizeMax || n==-1)   
+       if (n>=(IMG_INT32)ui32ScriptSizeMax || n==-1)   /* glibc >= 2.1 or glibc 2.0 */
        {
                PVR_DPF((PVR_DBG_ERROR, "Buffer overflow detected, pdump output may be incomplete."));
 
@@ -176,13 +210,19 @@ PVRSRV_ERROR PDumpOSVSprintf(IMG_CHAR *pszComment, IMG_UINT32 ui32ScriptSizeMax,
        return PVRSRV_OK;
 }
 
+/*!
+ * \name       PDumpOSDebugPrintf
+ */
 IMG_VOID PDumpOSDebugPrintf(IMG_CHAR* pszFormat, ...)
 {
        PVR_UNREFERENCED_PARAMETER(pszFormat);
 
-       
+       /* FIXME: Implement using services PVR_DBG or otherwise with kprintf */
 }
 
+/*!
+ * \name       PDumpOSSprintf
+ */
 PVRSRV_ERROR PDumpOSSprintf(IMG_CHAR *pszComment, IMG_UINT32 ui32ScriptSizeMax, IMG_CHAR *pszFormat, ...)
 {
        IMG_INT32 n;
@@ -194,7 +234,7 @@ PVRSRV_ERROR PDumpOSSprintf(IMG_CHAR *pszComment, IMG_UINT32 ui32ScriptSizeMax,
 
        va_end(vaArgs);
 
-       if (n>=(IMG_INT32)ui32ScriptSizeMax || n==-1)   
+       if (n>=(IMG_INT32)ui32ScriptSizeMax || n==-1)   /* glibc >= 2.1 or glibc 2.0 */
        {
                PVR_DPF((PVR_DBG_ERROR, "Buffer overflow detected, pdump output may be incomplete."));
 
@@ -204,6 +244,9 @@ PVRSRV_ERROR PDumpOSSprintf(IMG_CHAR *pszComment, IMG_UINT32 ui32ScriptSizeMax,
        return PVRSRV_OK;
 }
 
+/*!
+ * \name       PDumpOSBuflen
+ */
 IMG_UINT32 PDumpOSBuflen(IMG_HANDLE hBuffer, IMG_UINT32 ui32BufferSizeMax)
 {
        IMG_CHAR* pszBuf = hBuffer;
@@ -216,15 +259,18 @@ IMG_UINT32 PDumpOSBuflen(IMG_HANDLE hBuffer, IMG_UINT32 ui32BufferSizeMax)
        return(ui32Count);
 }
 
+/*!
+ * \name       PDumpOSVerifyLineEnding
+ */
 IMG_VOID PDumpOSVerifyLineEnding(IMG_HANDLE hBuffer, IMG_UINT32 ui32BufferSizeMax)
 {
        IMG_UINT32 ui32Count;
        IMG_CHAR* pszBuf = hBuffer;
 
-       
+       /* strlen */
        ui32Count = PDumpOSBuflen(hBuffer, ui32BufferSizeMax);
 
-       
+       /* Put \r \n sequence at the end if it isn't already there */
        if ((ui32Count >= 1) && (pszBuf[ui32Count-1] != '\n') && (ui32Count<ui32BufferSizeMax))
        {
                pszBuf[ui32Count] = '\n';
@@ -240,22 +286,34 @@ IMG_VOID PDumpOSVerifyLineEnding(IMG_HANDLE hBuffer, IMG_UINT32 ui32BufferSizeMa
        }
 }
 
+/*!
+ * \name       PDumpOSGetStream
+ */
 IMG_HANDLE PDumpOSGetStream(IMG_UINT32 ePDumpStream)
 {
        return (IMG_HANDLE)gsDBGPdumpState.psStream[ePDumpStream];
 }
 
+/*!
+ * \name       PDumpOSGetStreamOffset
+ */
 IMG_UINT32 PDumpOSGetStreamOffset(IMG_UINT32 ePDumpStream)
 {
        PDBG_STREAM psStream = gsDBGPdumpState.psStream[ePDumpStream];
        return gpfnDbgDrv->pfnGetStreamOffset(psStream);
 }
 
+/*!
+ * \name       PDumpOSGetParamFileNum
+ */
 IMG_UINT32 PDumpOSGetParamFileNum(IMG_VOID)
 {
        return gsDBGPdumpState.ui32ParamFileNum;
 }
 
+/*!
+ * \name       PDumpOSWriteString
+ */
 IMG_BOOL PDumpOSWriteString(IMG_HANDLE hStream,
                IMG_UINT8 *psui8Data,
                IMG_UINT32 ui32Size,
@@ -268,14 +326,21 @@ IMG_BOOL PDumpOSWriteString(IMG_HANDLE hStream,
                                        ui32Flags);
 }
 
+/*!
+ * \name       PDumpOSCheckForSplitting
+ */
 IMG_VOID PDumpOSCheckForSplitting(IMG_HANDLE hStream, IMG_UINT32 ui32Size, IMG_UINT32 ui32Flags)
 {
-       
+       /* File size limit not implemented for this OS.
+        */
        PVR_UNREFERENCED_PARAMETER(hStream);
        PVR_UNREFERENCED_PARAMETER(ui32Size);
        PVR_UNREFERENCED_PARAMETER(ui32Flags);
 }
 
+/*!
+ * \name       PDumpOSJTInitialised
+ */
 IMG_BOOL PDumpOSJTInitialised(IMG_VOID)
 {
        if(gpfnDbgDrv)
@@ -285,11 +350,17 @@ IMG_BOOL PDumpOSJTInitialised(IMG_VOID)
        return IMG_FALSE;
 }
 
+/*!
+ * \name       PDumpOSIsSuspended
+ */
 inline IMG_BOOL PDumpOSIsSuspended(IMG_VOID)
 {
        return (atomic_read(&gsPDumpSuspended) != 0) ? IMG_TRUE : IMG_FALSE;
 }
 
+/*!
+ * \name       PDumpOSCPUVAddrToDevPAddr
+ */
 IMG_VOID PDumpOSCPUVAddrToDevPAddr(PVRSRV_DEVICE_TYPE eDeviceType,
         IMG_HANDLE hOSMemHandle,
                IMG_UINT32 ui32Offset,
@@ -300,19 +371,23 @@ IMG_VOID PDumpOSCPUVAddrToDevPAddr(PVRSRV_DEVICE_TYPE eDeviceType,
        IMG_CPU_PHYADDR sCpuPAddr;
 
        PVR_UNREFERENCED_PARAMETER(pui8LinAddr);
-       PVR_UNREFERENCED_PARAMETER(ui32PageSize);   
+       PVR_UNREFERENCED_PARAMETER(ui32PageSize);   /* for when no assert */
 
-       
+       /* Caller must now alway supply hOSMemHandle, even though we only (presently)
+          use it here in the linux implementation */
           
        PVR_ASSERT (hOSMemHandle != IMG_NULL);
        
        sCpuPAddr = OSMemHandleToCpuPAddr(hOSMemHandle, ui32Offset);
        PVR_ASSERT((sCpuPAddr.uiAddr & (ui32PageSize - 1)) == 0);
 
-       
+       /* convert CPU physical addr to device physical */
        *psDevPAddr = SysCpuPAddrToDevPAddr(eDeviceType, sCpuPAddr);
 }
 
+/*!
+ * \name       PDumpOSCPUVAddrToPhysPages
+ */
 IMG_VOID PDumpOSCPUVAddrToPhysPages(IMG_HANDLE hOSMemHandle,
                IMG_UINT32 ui32Offset,
                IMG_PUINT8 pui8LinAddr,
@@ -321,7 +396,9 @@ IMG_VOID PDumpOSCPUVAddrToPhysPages(IMG_HANDLE hOSMemHandle,
 {
        if(hOSMemHandle)
        {
-               
+               /*
+                * If a Services memory handle is provided then use it.
+                */
                IMG_CPU_PHYADDR     sCpuPAddr;
 
                PVR_UNREFERENCED_PARAMETER(pui8LinAddr);
@@ -338,6 +415,9 @@ IMG_VOID PDumpOSCPUVAddrToPhysPages(IMG_HANDLE hOSMemHandle,
        }
 }
 
+/*!
+ *     \name   PDumpOSDebugDriverWrite
+ */
 IMG_UINT32 PDumpOSDebugDriverWrite( PDBG_STREAM psStream,
                                                                        PDUMP_DDWMODE eDbgDrvWriteMode,
                                                                        IMG_UINT8 *pui8Data,
@@ -365,29 +445,43 @@ IMG_UINT32 PDumpOSDebugDriverWrite( PDBG_STREAM psStream,
        return 0xFFFFFFFFU;
 }
 
+/*!
+ *     \name   PDumpOSReleaseExecution
+ */
 IMG_VOID PDumpOSReleaseExecution(IMG_VOID)
 {
        OSReleaseThreadQuanta();
 }
 
+/**************************************************************************
+ * Function Name  : PDumpInit
+ * Outputs        : None
+ * Returns        :
+ * Description    : Reset connection to vldbgdrv
+ *                                     Then try to connect to PDUMP streams
+**************************************************************************/
 IMG_VOID PDumpInit(IMG_VOID)
 {
        IMG_UINT32 i;
        DBGKM_CONNECT_NOTIFIER sConnectNotifier;
 
-       
+       /* If we tried this earlier, then we might have connected to the driver
+        * But if pdump.exe was running then the stream connected would fail
+        */
        if (!gpfnDbgDrv)
        {
-               DBGDrvGetServiceTable((IMG_VOID **)&gpfnDbgDrv);
+               DBGDrvGetServiceTable(&gpfnDbgDrv);
 
 
-               
+               // If something failed then no point in trying to connect streams
                if (gpfnDbgDrv == IMG_NULL)
                {
                        return;
                }
                
-               
+               /*
+                * Pass the connection notify callback
+                */
                sConnectNotifier.pfnConnectNotifier = &PDumpConnectionNotify;
                gpfnDbgDrv->pfnSetConnectNotifier(sConnectNotifier);
 
@@ -457,7 +551,9 @@ init_failed:
                gsDBGPdumpState.pszMsg = IMG_NULL;
        }
 
-       
+       /*
+        * Remove the connection notify callback
+        */
        sConnectNotifier.pfnConnectNotifier = 0;
        gpfnDbgDrv->pfnSetConnectNotifier(sConnectNotifier);
 
@@ -493,13 +589,22 @@ IMG_VOID PDumpDeInit(IMG_VOID)
                gsDBGPdumpState.pszMsg = IMG_NULL;
        }
 
-       
+       /*
+        * Remove the connection notify callback
+        */
        sConnectNotifier.pfnConnectNotifier = 0;
        gpfnDbgDrv->pfnSetConnectNotifier(sConnectNotifier);
 
        gpfnDbgDrv = IMG_NULL;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpStartInitPhaseKM
+ * Inputs         : None
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Resume init phase state
+**************************************************************************/
 PVRSRV_ERROR PDumpStartInitPhaseKM(IMG_VOID)
 {
        IMG_UINT32 i;
@@ -515,6 +620,13 @@ PVRSRV_ERROR PDumpStartInitPhaseKM(IMG_VOID)
        return PVRSRV_OK;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpStopInitPhaseKM
+ * Inputs         : None
+ * Outputs        : None
+ * Returns        : None
+ * Description    : End init phase state
+**************************************************************************/
 PVRSRV_ERROR PDumpStopInitPhaseKM(IMG_VOID)
 {
        IMG_UINT32 i;
@@ -531,12 +643,26 @@ PVRSRV_ERROR PDumpStopInitPhaseKM(IMG_VOID)
        return PVRSRV_OK;
 }
 
+/**************************************************************************
+ * Function Name  : PDumpIsLastCaptureFrameKM
+ * Inputs         : None
+ * Outputs        : None
+ * Returns        : True or false
+ * Description    : Tests whether the current frame is being pdumped
+**************************************************************************/
 IMG_BOOL PDumpIsLastCaptureFrameKM(IMG_VOID)
 {
        return gpfnDbgDrv->pfnIsLastCaptureFrame(gsDBGPdumpState.psStream[PDUMP_STREAM_SCRIPT2]);
 }
 
 
+/**************************************************************************
+ * Function Name  : PDumpIsCaptureFrameKM
+ * Inputs         : None
+ * Outputs        : None
+ * Returns        : True or false
+ * Description    : Tests whether the current frame is being pdumped
+**************************************************************************/
 IMG_BOOL PDumpOSIsCaptureFrameKM(IMG_VOID)
 {
        if (PDumpSuspended())
@@ -546,6 +672,13 @@ IMG_BOOL PDumpOSIsCaptureFrameKM(IMG_VOID)
        return gpfnDbgDrv->pfnIsCaptureFrame(gsDBGPdumpState.psStream[PDUMP_STREAM_SCRIPT2], IMG_FALSE);
 }
 
+/**************************************************************************
+ * Function Name  : PDumpSetFrameKM
+ * Inputs         : None
+ * Outputs        : None
+ * Returns        : None
+ * Description    : Sets a frame
+**************************************************************************/
 PVRSRV_ERROR PDumpOSSetFrameKM(IMG_UINT32 ui32Frame)
 {
        IMG_UINT32      ui32Stream;
@@ -562,12 +695,30 @@ PVRSRV_ERROR PDumpOSSetFrameKM(IMG_UINT32 ui32Frame)
 }
 
 
+/*****************************************************************************
+ FUNCTION      :       PDumpWriteString2
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_BOOL PDumpWriteString2(IMG_CHAR * pszString, IMG_UINT32 ui32Flags)
 {
        return PDumpWriteILock(gsDBGPdumpState.psStream[PDUMP_STREAM_SCRIPT2], (IMG_UINT8 *) pszString, strlen(pszString), ui32Flags);
 }
 
 
+/*****************************************************************************
+ FUNCTION      : PDumpWriteILock
+
+ PURPOSE       : Writes, making sure it all goes...
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_BOOL PDumpWriteILock(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_UINT32 ui32Count, IMG_UINT32 ui32Flags)
 {
        IMG_UINT32 ui32Written = 0;
@@ -578,7 +729,9 @@ static IMG_BOOL PDumpWriteILock(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_U
        }
 
 
-       
+       /*
+               Set the stream marker to split output files
+       */
 
        if (psStream == gsDBGPdumpState.psStream[PDUMP_STREAM_PARAM2])
        {
@@ -604,11 +757,31 @@ static IMG_BOOL PDumpWriteILock(PDBG_STREAM psStream, IMG_UINT8 *pui8Data, IMG_U
        return IMG_TRUE;
 }
 
+/*****************************************************************************
+ FUNCTION      :       DbgSetFrame
+
+ PURPOSE       :       Sets the frame in the stream
+
+ PARAMETERS    :       psStream        - Stream pointer
+                               ui32Frame               - Frame number to set
+
+ RETURNS       :       None
+*****************************************************************************/
 static IMG_VOID DbgSetFrame(PDBG_STREAM psStream, IMG_UINT32 ui32Frame)
 {
        gpfnDbgDrv->pfnSetFrame(psStream, ui32Frame);
 }
 
+/*****************************************************************************
+ FUNCTION      :       DbgSetMarker
+
+ PURPOSE       :       Sets the marker of the stream to split output files
+
+ PARAMETERS    :       psStream        - Stream pointer
+                               ui32Marker      - Marker number to set
+
+ RETURNS       :       None
+*****************************************************************************/
 static IMG_VOID DbgSetMarker(PDBG_STREAM psStream, IMG_UINT32 ui32Marker)
 {
        gpfnDbgDrv->pfnSetMarker(psStream, ui32Marker);
@@ -624,5 +797,8 @@ IMG_VOID PDumpResumeKM(IMG_VOID)
        atomic_dec(&gsPDumpSuspended);
 }
 
-#endif 
-#endif 
+#endif /* #if defined (PDUMP) */
+#endif /* #if defined (SUPPORT_SGX) */
+/*****************************************************************************
+ End of file (PDUMP.C)
+*****************************************************************************/
index b8751d3..6b09705 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linux private data structure
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __INCLUDED_PRIVATE_DATA_H_
 #define __INCLUDED_PRIVATE_DATA_H_
 #include <drm/drmP.h>
 #endif
 
+/* This structure is required in the rare case that a process creates
+ * a connection to services, but before closing the file descriptor,
+ * does a fork(). This fork() will duplicate the file descriptor in the
+ * child process. If the parent process dies before the child, this can
+ * cause the PVRSRVRelease() method to be called in a different process
+ * context than the original PVRSRVOpen(). This is bad because we need
+ * to update the per-process data reference count and/or free the
+ * per-process data. So we must keep a record of which PID's per-process
+ * data to inspect during ->release().
+ */
+
 typedef struct
 {
-       
+       /* PID that created this services connection */
        IMG_UINT32 ui32OpenPID;
 
-       
+       /* Global kernel MemInfo handle */
 #if defined (SUPPORT_SID_INTERFACE)
        IMG_SID hKernelMemInfo;
 #else
@@ -45,25 +71,25 @@ typedef struct
 #endif
 
 #if defined(SUPPORT_DRI_DRM) && defined(PVR_SECURE_DRM_AUTH_EXPORT)
-       
+       /* The private data is on a list in the per-process data structure */
        struct list_head sDRMAuthListItem;
 
        struct drm_file *psDRMFile;
 #endif
 
 #if defined(SUPPORT_MEMINFO_IDS)
-       
+       /* Globally unique "stamp" for kernel MemInfo */
        IMG_UINT64 ui64Stamp;
-#endif 
+#endif /* defined(SUPPORT_MEMINFO_IDS) */
 
-       
+       /* Accounting for OSAllocMem */
        IMG_HANDLE hBlockAlloc;
 
 #if defined(SUPPORT_DRI_DRM_EXT)
-       IMG_PVOID pPriv;        
+       IMG_PVOID pPriv;        /*private data for extending this struct*/
 #endif
 }
 PVRSRV_FILE_PRIVATE_DATA;
 
-#endif 
+#endif /* __INCLUDED_PRIVATE_DATA_H_ */
 
index 1df8aff..3824539 100644 (file)
@@ -1,28 +1,46 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Proc files implementation.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Functions for creating and reading proc filesystem entries.
+                Proc filesystem support must be built into the kernel for
+                these functions to be any use.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 
@@ -52,6 +70,7 @@
 
 #include "lists.h"
 
+// The proc entry for our /proc/pvr directory
 static struct proc_dir_entry * dir;
 
 static const IMG_CHAR PVRProcDirRoot[] = "pvr";
@@ -98,6 +117,28 @@ static void ProcSeqShowVersion(struct seq_file *sfile,void* el);
 static void ProcSeqShowSysNodes(struct seq_file *sfile,void* el);
 static void* ProcSeqOff2ElementSysNodes(struct seq_file * sfile, loff_t off);
 
+/*!
+******************************************************************************
+
+ @Function : printAppend
+
+ @Description
+
+ Print into the supplied buffer at the specified offset remaining within
+ the specified total buffer size.
+
+ @Input  size : the total size of the buffer
+
+ @Input  off : the offset into the buffer to start printing
+
+ @Input  format : the printf format string
+
+ @Input  ...    : format args
+
+ @Return : The number of chars now in the buffer (original value of 'off'
+           plus number of chars added); 'size' if full.
+
+*****************************************************************************/
 off_t printAppend(IMG_CHAR * buffer, size_t size, off_t off, const IMG_CHAR * format, ...)
 {
     IMG_INT n;
@@ -109,10 +150,13 @@ off_t printAppend(IMG_CHAR * buffer, size_t size, off_t off, const IMG_CHAR * fo
     n = vsnprintf (buffer+off, space, format, ap);
 
     va_end (ap);
-    
+    /* According to POSIX, n is greater than or equal to the size available if
+     * the print would have overflowed the buffer.  Other platforms may
+     * return -1 if printing was truncated.
+     */
     if (n >= (IMG_INT)space || n < 0)
     {
-       
+       /* Ensure final string is terminated */
         buffer[size - 1] = 0;
         return (off_t)(size - 1);
     }
@@ -123,16 +167,50 @@ off_t printAppend(IMG_CHAR * buffer, size_t size, off_t off, const IMG_CHAR * fo
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : ProcSeq1ElementOff2Element
+
+ @Description
+
+ Heleper Offset -> Element function for /proc files with only one entry
+ without header.
+
+ @Input  sfile : seq_file object related to /proc/ file
+
+ @Input  off : the offset into the buffer (id of object)
+
+ @Return : Pointer to element to be shown.
+
+*****************************************************************************/
 void* ProcSeq1ElementOff2Element(struct seq_file *sfile, loff_t off)
 {
        PVR_UNREFERENCED_PARAMETER(sfile);
-       
+       // Return anything that is not PVR_RPOC_SEQ_START_TOKEN and NULL
        if(!off)
                return (void*)2;
        return NULL;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : ProcSeq1ElementHeaderOff2Element
+
+ @Description
+
+ Heleper Offset -> Element function for /proc files with only one entry
+ with header.
+
+ @Input  sfile : seq_file object related to /proc/ file
+
+ @Input  off : the offset into the buffer (id of object)
+
+ @Return : Pointer to element to be shown.
+
+*****************************************************************************/
 void* ProcSeq1ElementHeaderOff2Element(struct seq_file *sfile, loff_t off)
 {
        PVR_UNREFERENCED_PARAMETER(sfile);
@@ -142,7 +220,7 @@ void* ProcSeq1ElementHeaderOff2Element(struct seq_file *sfile, loff_t off)
                return PVR_PROC_SEQ_START_TOKEN;
        }
 
-       
+       // Return anything that is not PVR_RPOC_SEQ_START_TOKEN and NULL
        if(off == 1)
                return (void*)2;
 
@@ -150,6 +228,22 @@ void* ProcSeq1ElementHeaderOff2Element(struct seq_file *sfile, loff_t off)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : pvr_proc_open
+
+ @Description
+ File opening function passed to proc_dir_entry->proc_fops for /proc entries
+ created by CreateProcReadEntrySeq.
+
+ @Input  inode : inode entry of opened /proc file
+
+ @Input  file : file entry of opened /proc file
+
+ @Return      : 0 if no errors
+
+*****************************************************************************/
 static IMG_INT pvr_proc_open(struct inode *inode,struct file *file)
 {
        IMG_INT ret = seq_open(file, &pvr_proc_seq_operations);
@@ -157,11 +251,22 @@ static IMG_INT pvr_proc_open(struct inode *inode,struct file *file)
        struct seq_file *seq = (struct seq_file*)file->private_data;
        struct proc_dir_entry* pvr_proc_entry = PDE(inode);
 
-       
+       /* Add pointer to handlers to seq_file structure */
        seq->private = pvr_proc_entry->data;
        return ret;
 }
 
+/*!
+******************************************************************************
+
+ @Function : pvr_proc_write
+
+ @Description
+ File writing function passed to proc_dir_entry->proc_fops for /proc files.
+ It's exacly the same function that is used as default one (->fs/proc/generic.c),
+ it calls proc_dir_entry->write_proc for writing procedure.
+
+*****************************************************************************/
 static ssize_t pvr_proc_write(struct file *file, const char __user *buffer,
                size_t count, loff_t *ppos)
 {
@@ -178,6 +283,23 @@ static ssize_t pvr_proc_write(struct file *file, const char __user *buffer,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : pvr_proc_seq_start
+
+ @Description
+ Seq_file start function. Detailed description of seq_file workflow can
+ be found here: http://tldp.org/LDP/lkmpg/2.6/html/x861.html.
+ This function ises off2element handler.
+
+ @Input  proc_seq_file : sequence file entry
+
+ @Input  pos : offset within file (id of entry)
+
+ @Return      : Pointer to element from we start enumeration (0 ends it)
+
+*****************************************************************************/
 static void *pvr_proc_seq_start (struct seq_file *proc_seq_file, loff_t *pos)
 {
        PVR_PROC_SEQ_HANDLERS *handlers = (PVR_PROC_SEQ_HANDLERS*)proc_seq_file->private;
@@ -186,6 +308,20 @@ static void *pvr_proc_seq_start (struct seq_file *proc_seq_file, loff_t *pos)
        return handlers->off2element(proc_seq_file, *pos);
 }
 
+/*!
+******************************************************************************
+
+ @Function : pvr_proc_seq_stop
+
+ @Description
+ Seq_file stop function. Detailed description of seq_file workflow can
+ be found here: http://tldp.org/LDP/lkmpg/2.6/html/x861.html.
+
+ @Input  proc_seq_file : sequence file entry
+
+ @Input  v : current element pointer
+
+*****************************************************************************/
 static void pvr_proc_seq_stop (struct seq_file *proc_seq_file, void *v)
 {
        PVR_PROC_SEQ_HANDLERS *handlers = (PVR_PROC_SEQ_HANDLERS*)proc_seq_file->private;
@@ -195,6 +331,25 @@ static void pvr_proc_seq_stop (struct seq_file *proc_seq_file, void *v)
                handlers->startstop(proc_seq_file, IMG_FALSE);
 }
 
+/*!
+******************************************************************************
+
+ @Function : pvr_proc_seq_next
+
+ @Description
+ Seq_file next element function. Detailed description of seq_file workflow can
+ be found here: http://tldp.org/LDP/lkmpg/2.6/html/x861.html.
+ It uses supplied 'next' handler for fetching next element (or 0 if there is no one)
+
+ @Input  proc_seq_file : sequence file entry
+
+ @Input  pos : offset within file (id of entry)
+
+ @Input  v : current element pointer
+
+ @Return   : next element pointer (or 0 if end)
+
+*****************************************************************************/
 static void *pvr_proc_seq_next (struct seq_file *proc_seq_file, void *v, loff_t *pos)
 {
        PVR_PROC_SEQ_HANDLERS *handlers = (PVR_PROC_SEQ_HANDLERS*)proc_seq_file->private;
@@ -204,6 +359,23 @@ static void *pvr_proc_seq_next (struct seq_file *proc_seq_file, void *v, loff_t
        return handlers->off2element(proc_seq_file, *pos);
 }
 
+/*!
+******************************************************************************
+
+ @Function : pvr_proc_seq_show
+
+ @Description
+ Seq_file show element function. Detailed description of seq_file workflow can
+ be found here: http://tldp.org/LDP/lkmpg/2.6/html/x861.html.
+ It call proper 'show' handler to show (dump) current element using seq_* functions
+
+ @Input  proc_seq_file : sequence file entry
+
+ @Input  v : current element pointer
+
+ @Return   : 0 if everything is OK
+
+*****************************************************************************/
 static int pvr_proc_seq_show (struct seq_file *proc_seq_file, void *v)
 {
        PVR_PROC_SEQ_HANDLERS *handlers = (PVR_PROC_SEQ_HANDLERS*)proc_seq_file->private;
@@ -213,6 +385,38 @@ static int pvr_proc_seq_show (struct seq_file *proc_seq_file, void *v)
 
 
 
+/*!
+******************************************************************************
+
+ @Function : CreateProcEntryInDirSeq
+
+ @Description
+
+ Create a file under the given directory.  These dynamic files can be used at
+ runtime to get or set information about the device. Whis version uses seq_file
+ interface
+
+ @Input  pdir : parent directory
+
+ @Input name : the name of the file to create
+
+ @Input data : aditional data that will be passed to handlers
+
+ @Input next_handler : the function to call to provide the next element. OPTIONAL, if not
+                                               supplied, then off2element function is used instead
+
+ @Input show_handler : the function to call to show element
+
+ @Input off2element_handler : the function to call when it is needed to translate offest to element
+
+ @Input startstop_handler : the function to call when output memory page starts or stops. OPTIONAL.
+
+ @Input  whandler : the function to interpret writes from the user
+
+ @Return Ptr to proc entry , 0 for failure
+
+
+*****************************************************************************/
 static struct proc_dir_entry* CreateProcEntryInDirSeq(
                                                                           struct proc_dir_entry *pdir,
                                                                           const IMG_CHAR * name,
@@ -259,7 +463,7 @@ static struct proc_dir_entry* CreateProcEntryInDirSeq(
                file->proc_fops = &pvr_proc_operations;
                file->write_proc = whandler;
 
-               
+               /* Pass the handlers */
                file->data =  kmalloc(sizeof(PVR_PROC_SEQ_HANDLERS), GFP_KERNEL);
                if(file->data)
                {
@@ -279,6 +483,35 @@ static struct proc_dir_entry* CreateProcEntryInDirSeq(
 }
 
 
+/*!
+******************************************************************************
+
+ @Function :  CreateProcReadEntrySeq
+
+ @Description
+
+ Create a file under /proc/pvr.  These dynamic files can be used at runtime
+ to get information about the device.  Creation WILL fail if proc support is
+ not compiled into the kernel.  That said, the Linux kernel is not even happy
+ to build without /proc support these days. This version uses seq_file structure
+ for handling content generation.
+
+ @Input name : the name of the file to create
+
+ @Input data : aditional data that will be passed to handlers
+
+ @Input next_handler : the function to call to provide the next element. OPTIONAL, if not
+                                               supplied, then off2element function is used instead
+
+ @Input show_handler : the function to call to show element
+
+ @Input off2element_handler : the function to call when it is needed to translate offest to element
+
+ @Input startstop_handler : the function to call when output memory page starts or stops. OPTIONAL.
+
+ @Return Ptr to proc entry , 0 for failure
+
+*****************************************************************************/
 struct proc_dir_entry* CreateProcReadEntrySeq (
                                                                const IMG_CHAR * name,
                                                                IMG_VOID* data,
@@ -297,6 +530,40 @@ struct proc_dir_entry* CreateProcReadEntrySeq (
                                                          NULL);
 }
 
+/*!
+******************************************************************************
+
+ @Function : CreateProcEntrySeq
+
+ @Description
+
+ @Description
+
+ Create a file under /proc/pvr.  These dynamic files can be used at runtime
+ to get information about the device.  Creation WILL fail if proc support is
+ not compiled into the kernel.  That said, the Linux kernel is not even happy
+ to build without /proc support these days. This version uses seq_file structure
+ for handling content generation and is fuller than CreateProcReadEntrySeq (it
+ supports write access);
+
+ @Input name : the name of the file to create
+
+ @Input data : aditional data that will be passed to handlers
+
+ @Input next_handler : the function to call to provide the next element. OPTIONAL, if not
+                                               supplied, then off2element function is used instead
+
+ @Input show_handler : the function to call to show element
+
+ @Input off2element_handler : the function to call when it is needed to translate offest to element
+
+ @Input startstop_handler : the function to call when output memory page starts or stops. OPTIONAL.
+
+ @Input  whandler : the function to interpret writes from the user
+
+ @Return Ptr to proc entry , 0 for failure
+
+*****************************************************************************/
 struct proc_dir_entry* CreateProcEntrySeq (
                                                                                        const IMG_CHAR * name,
                                                                                        IMG_VOID* data,
@@ -321,6 +588,37 @@ struct proc_dir_entry* CreateProcEntrySeq (
 
 
 
+/*!
+******************************************************************************
+
+ @Function : CreatePerProcessProcEntrySeq
+
+ @Description
+
+ Create a file under /proc/pvr/<current process ID>.  Apart from the
+ directory where the file is created, this works the same way as
+ CreateProcEntry. It's seq_file version.
+
+
+
+ @Input name : the name of the file to create
+
+ @Input data : aditional data that will be passed to handlers
+
+ @Input next_handler : the function to call to provide the next element. OPTIONAL, if not
+                                               supplied, then off2element function is used instead
+
+ @Input show_handler : the function to call to show element
+
+ @Input off2element_handler : the function to call when it is needed to translate offest to element
+
+ @Input startstop_handler : the function to call when output memory page starts or stops. OPTIONAL.
+
+ @Input  whandler : the function to interpret writes from the user
+
+ @Return Ptr to proc entry , 0 for failure
+
+*****************************************************************************/
 struct proc_dir_entry* CreatePerProcessProcEntrySeq (
                                                                          const IMG_CHAR * name,
                                                                  IMG_VOID* data,
@@ -379,6 +677,20 @@ struct proc_dir_entry* CreatePerProcessProcEntrySeq (
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : RemoveProcEntrySeq
+
+ @Description
+
+ Remove a single node (created using *Seq function) under /proc/pvr.
+
+ @Input proc_entry : structure returned by Create function.
+
+ @Return nothing
+
+*****************************************************************************/
 IMG_VOID RemoveProcEntrySeq( struct proc_dir_entry* proc_entry )
 {
     if (dir)
@@ -393,6 +705,22 @@ IMG_VOID RemoveProcEntrySeq( struct proc_dir_entry* proc_entry )
     }
 }
 
+/*!
+******************************************************************************
+
+ @Function : RemovePerProcessProcEntry Seq
+
+ @Description
+
+ Remove a single node under the per process proc directory (created by *Seq function).
+
+ Remove a single node (created using *Seq function) under /proc/pvr.
+
+ @Input proc_entry : structure returned by Create function.
+
+ @Return nothing
+
+*****************************************************************************/
 IMG_VOID RemovePerProcessProcEntrySeq(struct proc_dir_entry* proc_entry)
 {
     PVRSRV_ENV_PER_PROCESS_DATA *psPerProc;
@@ -420,10 +748,46 @@ IMG_VOID RemovePerProcessProcEntrySeq(struct proc_dir_entry* proc_entry)
     }
 }
 
+/*!
+******************************************************************************
+
+ @Function : pvr_read_proc_vm
+
+ @Description
+
+ When the user accesses the proc filesystem entry for the device, we are
+ called here to create the content for the 'file'.  We can print anything we
+ want here.  If the info we want to return is too big for one page ('count'
+ chars), we return successive chunks on each call. For a number of ways of
+ achieving this, refer to proc_file_read() in linux/fs/proc/generic.c.
+
+ Here, as we are accessing lists of information, we output '1' in '*start' to
+ instruct proc to advance 'off' by 1 on each call.  The number of chars placed
+ in the buffer is returned.  Multiple calls are made here by the proc
+ filesystem until we set *eof.  We can return zero without setting eof to
+ instruct proc to flush 'page' (causing it to be printed) if there is not
+ enough space left (eg for a complete line).
+
+ @Input  page : where to write the output
+
+ @Input  start : memory location into which should be written next offset
+                 to read from.
+
+ @Input  off : the offset into the /proc file being read
+
+ @Input  count : the size of the buffer 'page'
+
+ @Input  eof : memory location into which 1 should be written when at EOF
+
+ @Input  data : data specific to this /proc file entry
+
+ @Return      : length of string written to page
+
+*****************************************************************************/
 static IMG_INT pvr_read_proc(IMG_CHAR *page, IMG_CHAR **start, off_t off,
                          IMG_INT count, IMG_INT *eof, IMG_VOID *data)
 {
-        
+       /* PRQA S 0307 1 */ /* ignore warning about casting to different pointer type */
     pvr_read_proc_t *pprn = (pvr_read_proc_t *)data;
 
     off_t len = pprn (page, (size_t)count, off);
@@ -433,9 +797,9 @@ static IMG_INT pvr_read_proc(IMG_CHAR *page, IMG_CHAR **start, off_t off,
         len  = 0;
         *eof = 1;
     }
-    else if (!len)             
+    else if (!len)             /* not enough space in the buffer */
     {
-        *start = (IMG_CHAR *) 0;   
+        *start = (IMG_CHAR *) 0;   /* don't advance the offset */
     }
     else
     {
@@ -446,6 +810,27 @@ static IMG_INT pvr_read_proc(IMG_CHAR *page, IMG_CHAR **start, off_t off,
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : CreateProcEntryInDir
+
+ @Description
+
+ Create a file under the given directory.  These dynamic files can be used at
+ runtime to get or set information about the device.
+
+ @Input  pdir : parent directory
+
+ @Input  name : the name of the file to create
+
+ @Input  rhandler : the function to supply the content
+
+ @Input  whandler : the function to interpret writes from the user
+
+ @Return success code : 0 or -errno.
+
+*****************************************************************************/
 static IMG_INT CreateProcEntryInDir(struct proc_dir_entry *pdir, const IMG_CHAR * name, read_proc_t rhandler, write_proc_t whandler, IMG_VOID *data)
 {
     struct proc_dir_entry * file;
@@ -492,12 +877,54 @@ static IMG_INT CreateProcEntryInDir(struct proc_dir_entry *pdir, const IMG_CHAR
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : CreateProcEntry
+
+ @Description
+
+ Create a file under /proc/pvr.  These dynamic files can be used at runtime
+ to get or set information about the device.
+
+ This interface is fuller than CreateProcReadEntry, and supports write access;
+ it is really just a wrapper for the native linux functions.
+
+ @Input  name : the name of the file to create under /proc/pvr
+
+ @Input  rhandler : the function to supply the content
+
+ @Input  whandler : the function to interpret writes from the user
+
+ @Return success code : 0 or -errno.
+
+*****************************************************************************/
 IMG_INT CreateProcEntry(const IMG_CHAR * name, read_proc_t rhandler, write_proc_t whandler, IMG_VOID *data)
 {
     return CreateProcEntryInDir(dir, name, rhandler, whandler, data);
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : CreatePerProcessProcEntry
+
+ @Description
+
+ Create a file under /proc/pvr/<current process ID>.  Apart from the
+ directory where the file is created, this works the same way as
+ CreateProcEntry.
+
+ @Input  name : the name of the file to create under the per process /proc directory
+
+ @Input  rhandler : the function to supply the content
+
+ @Input  whandler : the function to interpret writes from the user
+
+ @Return success code : 0 or -errno.
+
+*****************************************************************************/
 IMG_INT CreatePerProcessProcEntry(const IMG_CHAR * name, read_proc_t rhandler, write_proc_t whandler, IMG_VOID *data)
 {
     PVRSRV_ENV_PER_PROCESS_DATA *psPerProc;
@@ -549,6 +976,25 @@ IMG_INT CreatePerProcessProcEntry(const IMG_CHAR * name, read_proc_t rhandler, w
 }
 
 
+/*!
+******************************************************************************
+
+ @Function :  CreateProcReadEntry
+
+ @Description
+
+ Create a file under /proc/pvr.  These dynamic files can be used at runtime
+ to get information about the device.  Creation WILL fail if proc support is
+ not compiled into the kernel.  That said, the Linux kernel is not even happy
+ to build without /proc support these days.
+
+ @Input name : the name of the file to create
+
+ @Input handler : the function to call to provide the content
+
+ @Return 0 for success, -errno for failure
+
+*****************************************************************************/
 IMG_INT CreateProcReadEntry(const IMG_CHAR * name, pvr_read_proc_t handler)
 {
     struct proc_dir_entry * file;
@@ -560,7 +1006,7 @@ IMG_INT CreateProcReadEntry(const IMG_CHAR * name, pvr_read_proc_t handler)
         return -ENOMEM;
     }
 
-        
+       /* PRQA S 0307 1 */ /* ignore warning about casting to different pointer type */
     file = create_proc_read_entry (name, S_IFREG | S_IRUGO, dir, pvr_read_proc, (IMG_VOID *)handler);
 
     if (file)
@@ -577,6 +1023,23 @@ IMG_INT CreateProcReadEntry(const IMG_CHAR * name, pvr_read_proc_t handler)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : CreateProcEntries
+
+ @Description
+
+ Create a directory /proc/pvr and the necessary entries within it.  These
+ dynamic files can be used at runtime to get information about the device.
+ Creation might fail if proc support is not compiled into the kernel or if
+ there is no memory
+
+ @Input none
+
+ @Return nothing
+
+*****************************************************************************/
 IMG_INT CreateProcEntries(IMG_VOID)
 {
     dir = proc_mkdir (PVRProcDirRoot, NULL);
@@ -631,6 +1094,20 @@ IMG_INT CreateProcEntries(IMG_VOID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : RemoveProcEntry
+
+ @Description
+
+ Remove a single node under /proc/pvr.
+
+ @Input name : the name of the node to remove
+
+ @Return nothing
+
+*****************************************************************************/
 IMG_VOID RemoveProcEntry(const IMG_CHAR * name)
 {
     if (dir)
@@ -641,6 +1118,20 @@ IMG_VOID RemoveProcEntry(const IMG_CHAR * name)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : RemovePerProcessProcEntry
+
+ @Description
+
+ Remove a single node under the per process proc directory.
+
+ @Input name : the name of the node to remove
+
+ @Return nothing
+
+*****************************************************************************/
 IMG_VOID RemovePerProcessProcEntry(const IMG_CHAR *name)
 {
     PVRSRV_ENV_PER_PROCESS_DATA *psPerProc;
@@ -666,6 +1157,20 @@ IMG_VOID RemovePerProcessProcEntry(const IMG_CHAR *name)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function : RemovePerProcessProcDir
+
+ @Description
+
+ Remove the per process directorty under /proc/pvr.
+
+ @Input psPerProc : environment specific per process data
+
+ @Return nothing
+
+*****************************************************************************/
 IMG_VOID RemovePerProcessProcDir(PVRSRV_ENV_PER_PROCESS_DATA *psPerProc)
 {
     if (psPerProc->psProcDir)
@@ -680,13 +1185,28 @@ IMG_VOID RemovePerProcessProcDir(PVRSRV_ENV_PER_PROCESS_DATA *psPerProc)
     }
 }
 
+/*!
+******************************************************************************
+
+ @Function    : RemoveProcEntries
+
+ Description
+
+ Proc filesystem entry deletion - Remove all proc filesystem entries for
+ the driver.
+
+ @Input none
+
+ @Return nothing
+
+*****************************************************************************/
 IMG_VOID RemoveProcEntries(IMG_VOID)
 {
 #ifdef DEBUG
        RemoveProcEntrySeq( g_pProcDebugLevel );
 #ifdef PVR_MANUAL_POWER_CONTROL
        RemoveProcEntrySeq( g_pProcPowerLevel );
-#endif 
+#endif /* PVR_MANUAL_POWER_CONTROL */
 #endif
 
        RemoveProcEntrySeq(g_pProcQueue);
@@ -703,6 +1223,14 @@ IMG_VOID RemoveProcEntries(IMG_VOID)
        remove_proc_entry(PVRProcDirRoot, NULL);
 }
 
+/*****************************************************************************
+ FUNCTION      :       ProcSeqShowVersion
+
+ PURPOSE       :       Print the content of version to /proc file
+
+ PARAMETERS    :       sfile - /proc seq_file
+                               el - Element to print
+*****************************************************************************/
 static void ProcSeqShowVersion(struct seq_file *sfile,void* el)
 {
        SYS_DATA *psSysData;
@@ -726,6 +1254,24 @@ static void ProcSeqShowVersion(struct seq_file *sfile,void* el)
        seq_printf( sfile, "System Version String: %s\n", pszSystemVersionString);
 }
 
+/*!
+******************************************************************************
+
+ @Function     procDumpSysNodes (plus deviceTypeToString and deviceClassToString)
+
+ @Description
+
+ Format the contents of /proc/pvr/nodes
+
+ @Input buf : where to place format contents data.
+
+ @Input size : the size of the buffer into which to place data
+
+ @Input off : how far into the file we are.
+
+ @Return   amount of data placed in buffer, 0, or END_OF_FILE :
+
+******************************************************************************/
 static const IMG_CHAR *deviceTypeToString(PVRSRV_DEVICE_TYPE deviceType)
 {
     switch (deviceType)
@@ -781,6 +1327,14 @@ static IMG_VOID* DecOffPsDev_AnyVaCb(PVRSRV_DEVICE_NODE *psNode, va_list va)
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       ProcSeqShowSysNodes
+
+ PURPOSE       :       Print the content of version to /proc file
+
+ PARAMETERS    :       sfile - /proc seq_file
+                               el - Element to print
+*****************************************************************************/
 static void ProcSeqShowSysNodes(struct seq_file *sfile,void* el)
 {
        PVRSRV_DEVICE_NODE *psDevNode;
@@ -807,6 +1361,16 @@ static void ProcSeqShowSysNodes(struct seq_file *sfile,void* el)
                          psDevNode->hResManContext);
 }
 
+/*****************************************************************************
+ FUNCTION      :       ProcSeqOff2ElementSysNodes
+
+ PURPOSE       :       Transale offset to element (/proc stuff)
+
+ PARAMETERS    :       sfile - /proc seq_file
+                               off - the offset into the buffer
+
+ RETURNS    :   element to print
+*****************************************************************************/
 static void* ProcSeqOff2ElementSysNodes(struct seq_file * sfile, loff_t off)
 {
     SYS_DATA *psSysData;
@@ -822,14 +1386,17 @@ static void* ProcSeqOff2ElementSysNodes(struct seq_file * sfile, loff_t off)
     psSysData = SysAcquireDataNoCheck();
     if (psSysData != IMG_NULL)
     {
-       
+       /* Find Dev Node */
        psDevNode = (PVRSRV_DEVICE_NODE*)
                        List_PVRSRV_DEVICE_NODE_Any_va(psSysData->psDeviceNodeList,
                                                                                                        DecOffPsDev_AnyVaCb,
                                                                                                        &off);
     }
 
-    
+    /* Return anything that is not PVR_RPOC_SEQ_START_TOKEN and NULL */
     return (void*)psDevNode;
 }
 
+/*****************************************************************************
+ End of file (proc.c)
+*****************************************************************************/
index 2066d71..bc2a554 100644 (file)
@@ -1,35 +1,52 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Proc interface definition.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Functions for creating and reading proc filesystem entries.
+                Refer to proc.c
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __SERVICES_PROC_H__
 #define __SERVICES_PROC_H__
 
-#include <asm/system.h>                
-#include <linux/proc_fs.h>     
-#include <linux/seq_file.h> 
+#include <asm/system.h>                // va_list etc
+#include <linux/proc_fs.h>     // read_proc_t etc
+#include <linux/seq_file.h> // seq_file
 
 #define END_OF_FILE (off_t) -1
 
@@ -51,8 +68,10 @@ typedef struct _PVR_PROC_SEQ_HANDLERS_ {
 } PVR_PROC_SEQ_HANDLERS;
 
 
+/** off2element function for elements with only ONE element (no header) */
 void* ProcSeq1ElementOff2Element(struct seq_file *sfile, loff_t off);
 
+/** off2element function for elements with only ONE element (+ header) */
 void* ProcSeq1ElementHeaderOff2Element(struct seq_file *sfile, loff_t off);
 
 off_t printAppend(IMG_CHAR * buffer, size_t size, off_t off, const IMG_CHAR * format, ...)
index 2615661..5d1ad8c 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          PVR Bridge Module (kernel side)
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Receives calls from the user portion of services and
+                despatches them to functions in the kernel portion.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "img_defs.h"
 #include "services.h"
@@ -36,6 +53,8 @@
 #include "linkage.h"
 #include "pvr_bridge_km.h"
 #include "pvr_uaccess.h"
+#include "refcount.h"
+#include "buffer_manager.h"
 
 #if defined(SUPPORT_DRI_DRM)
 #include <drm/drmP.h>
 #endif
 #endif
 
+/* VGX: */
 #if defined(SUPPORT_VGX)
 #include "vgx_bridge.h"
 #endif
 
+/* SGX: */
 #if defined(SUPPORT_SGX)
 #include "sgx_bridge.h"
 #endif
@@ -75,7 +96,7 @@ extern PVRSRV_LINUX_MUTEX gPVRSRVLock;
 
 #if defined(SUPPORT_MEMINFO_IDS)
 static IMG_UINT64 ui64Stamp;
-#endif 
+#endif /* defined(SUPPORT_MEMINFO_IDS) */
 
 PVRSRV_ERROR
 LinuxBridgeInit(IMG_VOID)
@@ -109,6 +130,13 @@ LinuxBridgeDeInit(IMG_VOID)
 
 #if defined(DEBUG_BRIDGE_KM)
 
+/*
+ * Lock MMap regions list (called on page start/stop while reading /proc/mmap)
+ *
+ * sfile : seq_file that handles /proc file
+ * start : TRUE if it's start, FALSE if it's stop
+ *  
+ */
 static void ProcSeqStartstopBridgeStats(struct seq_file *sfile,IMG_BOOL start) 
 {
        if(start) 
@@ -122,6 +150,16 @@ static void ProcSeqStartstopBridgeStats(struct seq_file *sfile,IMG_BOOL start)
 }
 
 
+/*
+ * Convert offset (index from KVOffsetTable) to element 
+ * (called when reading /proc/mmap file)
+
+ * sfile : seq_file that handles /proc file
+ * off : index into the KVOffsetTable from which to print
+ *  
+ * returns void* : Pointer to element that will be dumped
+ *  
+*/
 static void* ProcSeqOff2ElementBridgeStats(struct seq_file *sfile, loff_t off)
 {
        if(!off) 
@@ -138,12 +176,28 @@ static void* ProcSeqOff2ElementBridgeStats(struct seq_file *sfile, loff_t off)
        return (void*)&g_BridgeDispatchTable[off-1];
 }
 
+/*
+ * Gets next MMap element to show. (called when reading /proc/mmap file)
+
+ * sfile : seq_file that handles /proc file
+ * el : actual element
+ * off : index into the KVOffsetTable from which to print
+ *  
+ * returns void* : Pointer to element to show (0 ends iteration)
+*/
 static void* ProcSeqNextBridgeStats(struct seq_file *sfile,void* el,loff_t off)
 {
        return ProcSeqOff2ElementBridgeStats(sfile,off);
 }
 
 
+/*
+ * Show MMap element (called when reading /proc/mmap file)
+
+ * sfile : seq_file that handles /proc file
+ * el : actual element
+ *  
+*/
 static void ProcSeqShowBridgeStats(struct seq_file *sfile,void* el)
 {
        PVRSRV_BRIDGE_DISPATCH_TABLE_ENTRY *psEntry = ( PVRSRV_BRIDGE_DISPATCH_TABLE_ENTRY*)el;
@@ -178,7 +232,7 @@ static void ProcSeqShowBridgeStats(struct seq_file *sfile,void* el)
                                   psEntry->ui32CopyToUserTotalBytes);
 }
 
-#endif 
+#endif /* DEBUG_BRIDGE_KM */
 
 
 #if defined(SUPPORT_DRI_DRM)
@@ -217,7 +271,9 @@ PVRSRV_BridgeDispatchKM(struct file *pFile, unsigned int unref__ ioctlCmd, unsig
                goto unlock_and_return;
        }
        
-       
+       /* FIXME - Currently the CopyFromUserWrapper which collects stats about
+        * how much data is shifted to/from userspace isn't available to us
+        * here. */
        if(OSCopyFromUser(IMG_NULL,
                                          psBridgePackageKM,
                                          psBridgePackageUM,
@@ -255,7 +311,7 @@ PVRSRV_BridgeDispatchKM(struct file *pFile, unsigned int unref__ ioctlCmd, unsig
        }
        else
        {
-               
+               /* lookup per-process data for this process */
                psPerProc = PVRSRVPerProcessData(ui32PID);
                if(psPerProc == IMG_NULL)
                {
@@ -334,7 +390,13 @@ PVRSRV_BridgeDispatchKM(struct file *pFile, unsigned int unref__ ioctlCmd, unsig
                                break;
                        }
 
-                       
+                       /*
+                        * The DRM file structure we are using for Services
+                        * is not one that DRI authentication was done on.
+                        * Look for an authenticated file structure for
+                        * this process, making sure the DRM master is the
+                        * same as ours.
+                        */
                        psEnvPerProc = (PVRSRV_ENV_PER_PROCESS_DATA *)PVRSRVProcessPrivateData(psPerProc);
                        if (psEnvPerProc == IMG_NULL)
                        {
@@ -368,7 +430,7 @@ PVRSRV_BridgeDispatchKM(struct file *pFile, unsigned int unref__ ioctlCmd, unsig
                default:
                        break;
        }
-#endif 
+#endif /* defined(SUPPORT_DRI_DRM) && defined(PVR_SECURE_DRM_AUTH_EXPORT) */
 
        err = BridgedDispatchKM(psPerProc, psBridgePackageKM);
        if(err != PVRSRV_OK)
@@ -381,15 +443,40 @@ PVRSRV_BridgeDispatchKM(struct file *pFile, unsigned int unref__ ioctlCmd, unsig
                        PVRSRV_BRIDGE_OUT_EXPORTDEVICEMEM *psExportDeviceMemOUT =
                                (PVRSRV_BRIDGE_OUT_EXPORTDEVICEMEM *)psBridgePackageKM->pvParamOut;
                        PVRSRV_FILE_PRIVATE_DATA *psPrivateData = PRIVATE_DATA(pFile);
+                       IMG_HANDLE hMemInfo;
+                       PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo;
 
-                       if (pvr_get_user(psPrivateData->hKernelMemInfo, &psExportDeviceMemOUT->hMemInfo) != 0)
+                       if (pvr_get_user(hMemInfo, &psExportDeviceMemOUT->hMemInfo) != 0)
                        {
                                err = -EFAULT;
                                goto unlock_and_return;
                        }
+
+                       /* Look up the meminfo we just exported */
+                       if(PVRSRVLookupHandle(KERNEL_HANDLE_BASE,
+                                                                 (IMG_PVOID *)&psKernelMemInfo,
+                                                                 hMemInfo,
+                                                                 PVRSRV_HANDLE_TYPE_MEM_INFO) != PVRSRV_OK)
+                       {
+                               PVR_DPF((PVR_DBG_ERROR, "%s: Failed to look up export handle", __FUNCTION__));
+                               err = -EFAULT;
+                               goto unlock_and_return;
+                       }
+
+                       /* Bump the refcount; decremented on release of the fd */
+                       PVRSRVKernelMemInfoIncRef(psKernelMemInfo);
+
+                       /* Tell the XProc about the export if required */
+                       if (psKernelMemInfo->sShareMemWorkaround.bInUse)
+                       {
+                               BM_XProcIndexAcquire(psKernelMemInfo->sShareMemWorkaround.ui32ShareIndex);
+                       }
+
+                       psPrivateData->hKernelMemInfo = hMemInfo;
 #if defined(SUPPORT_MEMINFO_IDS)
                        psPrivateData->ui64Stamp = ++ui64Stamp;
 
+                       psKernelMemInfo->ui64Stamp = psPrivateData->ui64Stamp;
                        if (pvr_put_user(psPrivateData->ui64Stamp, &psExportDeviceMemOUT->ui64Stamp) != 0)
                        {
                                err = -EFAULT;
@@ -401,6 +488,7 @@ PVRSRV_BridgeDispatchKM(struct file *pFile, unsigned int unref__ ioctlCmd, unsig
 
 #if defined(SUPPORT_MEMINFO_IDS)
                case PVRSRV_BRIDGE_MAP_DEV_MEMORY:
+               case PVRSRV_BRIDGE_MAP_DEV_MEMORY_2:
                {
                        PVRSRV_BRIDGE_OUT_MAP_DEV_MEMORY *psMapDeviceMemoryOUT =
                                (PVRSRV_BRIDGE_OUT_MAP_DEV_MEMORY *)psBridgePackageKM->pvParamOut;
@@ -424,7 +512,7 @@ PVRSRV_BridgeDispatchKM(struct file *pFile, unsigned int unref__ ioctlCmd, unsig
                        }
                        break;
                }
-#endif 
+#endif /* defined(SUPPORT_MEMINFO_IDS) */
 
                default:
                        break;
index 991bb51..04e42ad 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Debug Functionality
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provides kernel side Debug Functionality
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <linux/version.h>
 
@@ -38,7 +54,7 @@
 #include <linux/hardirq.h>
 #include <linux/module.h>
 #include <linux/spinlock.h>
-#include <linux/string.h>                      
+#include <linux/string.h>                      // strncpy, strlen
 #include <stdarg.h>
 #include "img_types.h"
 #include "servicesext.h"
 #include "linkage.h"
 #include "pvr_uaccess.h"
 
+#if !defined(CONFIG_PREEMPT)
+#define        PVR_DEBUG_ALWAYS_USE_SPINLOCK
+#endif
+
 static IMG_BOOL VBAppend(IMG_CHAR *pszBuf, IMG_UINT32 ui32BufSiz,
                                                 const IMG_CHAR* pszFormat, va_list VArgs)
                                                 IMG_FORMAT_PRINTF(3, 0);
@@ -62,68 +82,96 @@ static IMG_BOOL BAppend(IMG_CHAR *pszBuf, IMG_UINT32 ui32BufSiz,
                                                const IMG_CHAR *pszFormat, ...)
                                                IMG_FORMAT_PRINTF(3, 4);
 
+/* NOTE: Must NOT be static! Used in module.c.. */
 IMG_UINT32 gPVRDebugLevel =
        (DBGPRIV_FATAL | DBGPRIV_ERROR | DBGPRIV_WARNING);
 
-#endif 
+#endif /* defined(PVRSRV_NEED_PVR_DPF) || defined(PVRSRV_NEED_PVR_TRACE) */
 
 #define        PVR_MAX_MSG_LEN PVR_MAX_DEBUG_MESSAGE_LEN
 
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
+/* Message buffer for non-IRQ messages */
 static IMG_CHAR gszBufferNonIRQ[PVR_MAX_MSG_LEN + 1];
+#endif
 
+/* Message buffer for IRQ messages */
 static IMG_CHAR gszBufferIRQ[PVR_MAX_MSG_LEN + 1];
 
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
+/* The lock is used to control access to gszBufferNonIRQ */
 static PVRSRV_LINUX_MUTEX gsDebugMutexNonIRQ;
+#endif
 
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,39))
+/* The lock is used to control access to gszBufferIRQ */
+/* PRQA S 0671,0685 1 */ /* ignore warnings about C99 style initialisation */
 static spinlock_t gsDebugLockIRQ = SPIN_LOCK_UNLOCKED;
 #else
 static DEFINE_SPINLOCK(gsDebugLockIRQ);
 #endif
 
-#if !defined (USE_SPIN_LOCK)  
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
+#if !defined (USE_SPIN_LOCK) /* to keep QAC happy */ 
 #define        USE_SPIN_LOCK (in_interrupt() || !preemptible())
 #endif
+#endif
 
 static inline void GetBufferLock(unsigned long *pulLockFlags)
 {
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
        if (USE_SPIN_LOCK)
+#endif
        {
                spin_lock_irqsave(&gsDebugLockIRQ, *pulLockFlags);
        }
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
        else
        {
                LinuxLockMutex(&gsDebugMutexNonIRQ);
        }
+#endif
 }
 
 static inline void ReleaseBufferLock(unsigned long ulLockFlags)
 {
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
        if (USE_SPIN_LOCK)
+#endif
        {
                spin_unlock_irqrestore(&gsDebugLockIRQ, ulLockFlags);
        }
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
        else
        {
                LinuxUnLockMutex(&gsDebugMutexNonIRQ);
        }
+#endif
 }
 
 static inline void SelectBuffer(IMG_CHAR **ppszBuf, IMG_UINT32 *pui32BufSiz)
 {
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
        if (USE_SPIN_LOCK)
+#endif
        {
                *ppszBuf = gszBufferIRQ;
                *pui32BufSiz = sizeof(gszBufferIRQ);
        }
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
        else
        {
                *ppszBuf = gszBufferNonIRQ;
                *pui32BufSiz = sizeof(gszBufferNonIRQ);
        }
+#endif
 }
 
+/*
+ * Append a string to a buffer using formatted conversion.
+ * The function takes a variable number of arguments, pointed
+ * to by the var args list.
+ */
 static IMG_BOOL VBAppend(IMG_CHAR *pszBuf, IMG_UINT32 ui32BufSiz, const IMG_CHAR* pszFormat, va_list VArgs)
 {
        IMG_UINT32 ui32Used;
@@ -137,15 +185,27 @@ static IMG_BOOL VBAppend(IMG_CHAR *pszBuf, IMG_UINT32 ui32BufSiz, const IMG_CHAR
        i32Len = vsnprintf(&pszBuf[ui32Used], ui32Space, pszFormat, VArgs);
        pszBuf[ui32BufSiz - 1] = 0;
 
-       
+       /* Return true if string was truncated */
        return (i32Len < 0 || i32Len >= (IMG_INT32)ui32Space) ? IMG_TRUE : IMG_FALSE;
 }
 
+/* Actually required for ReleasePrintf too */
+
 IMG_VOID PVRDPFInit(IMG_VOID)
 {
+#if !defined(PVR_DEBUG_ALWAYS_USE_SPINLOCK)
     LinuxInitMutex(&gsDebugMutexNonIRQ);
+#endif
 }
 
+/*!
+******************************************************************************
+       @Function    PVRSRVReleasePrintf
+       @Description To output an important message to the user in release builds
+       @Input       pszFormat - The message format string
+       @Input       ... - Zero or more arguments for use by the format string
+       @Return      None
+ ******************************************************************************/
 IMG_VOID PVRSRVReleasePrintf(const IMG_CHAR *pszFormat, ...)
 {
        va_list vaArgs;
@@ -174,18 +234,16 @@ IMG_VOID PVRSRVReleasePrintf(const IMG_CHAR *pszFormat, ...)
 
 }
 
-#if defined(PVRSRV_NEED_PVR_ASSERT)
-
-IMG_VOID PVRSRVDebugAssertFail(const IMG_CHAR* pszFile, IMG_UINT32 uLine)
-{
-       PVRSRVDebugPrintf(DBGPRIV_FATAL, pszFile, uLine, "Debug assertion failed!");
-       BUG();
-}
-
-#endif 
-
 #if defined(PVRSRV_NEED_PVR_TRACE)
 
+/*!
+******************************************************************************
+       @Function    PVRTrace
+       @Description To output a debug message to the user
+       @Input       pszFormat - The message format string
+       @Input       ... - Zero or more arguments for use by the format string
+       @Return      None
+ ******************************************************************************/
 IMG_VOID PVRSRVTrace(const IMG_CHAR* pszFormat, ...)
 {
        va_list VArgs;
@@ -215,10 +273,15 @@ IMG_VOID PVRSRVTrace(const IMG_CHAR* pszFormat, ...)
        va_end(VArgs);
 }
 
-#endif 
+#endif /* defined(PVRSRV_NEED_PVR_TRACE) */
 
 #if defined(PVRSRV_NEED_PVR_DPF)
 
+/*
+ * Append a string to a buffer using formatted conversion.
+ * The function takes a variable number of arguments, calling
+ * VBAppend to do the actual work.
+ */
 static IMG_BOOL BAppend(IMG_CHAR *pszBuf, IMG_UINT32 ui32BufSiz, const IMG_CHAR *pszFormat, ...)
 {
        va_list VArgs;
@@ -233,6 +296,17 @@ static IMG_BOOL BAppend(IMG_CHAR *pszBuf, IMG_UINT32 ui32BufSiz, const IMG_CHAR
        return bTrunc;
 }
 
+/*!
+******************************************************************************
+       @Function    PVRSRVDebugPrintf
+       @Description To output a debug message to the user
+       @Input       uDebugLevel - The current debug level
+       @Input       pszFile - The source file generating the message
+       @Input       uLine - The line of the source file
+       @Input       pszFormat - The message format string
+       @Input       ... - Zero or more arguments for use by the format string
+       @Return      None
+ ******************************************************************************/
 IMG_VOID PVRSRVDebugPrintf     (
                                                IMG_UINT32      ui32DebugLevel,
                                                const IMG_CHAR* pszFullFileName,
@@ -261,7 +335,7 @@ IMG_VOID PVRSRVDebugPrintf  (
 
                GetBufferLock(&ulLockFlags);
 
-               
+               /* Add in the level of warning */
                if (bTrace == IMG_FALSE)
                {
                        switch(ui32DebugLevel)
@@ -309,21 +383,22 @@ IMG_VOID PVRSRVDebugPrintf        (
                }
                else
                {
-                       
+                       /* Traces don't need a location */
                        if (bTrace == IMG_FALSE)
                        {
 #ifdef DEBUG_LOG_PATH_TRUNCATE
-                               
+                               /* Buffer for rewriting filepath in log messages */
                                static IMG_CHAR szFileNameRewrite[PVR_MAX_FILEPATH_LEN];
 
                                IMG_CHAR* pszTruncIter;
                                IMG_CHAR* pszTruncBackInter;
 
-                               
+                               /* Truncate path (DEBUG_LOG_PATH_TRUNCATE shoud be set to EURASIA env var)*/
                                if (strlen(pszFullFileName) > strlen(DEBUG_LOG_PATH_TRUNCATE)+1)
                                        pszFileName = pszFullFileName + strlen(DEBUG_LOG_PATH_TRUNCATE)+1;
 
-                               
+                               /* Try to find '/../' entries and remove it together with
+                                  previous entry. Repeat unit all removed */
                                strncpy(szFileNameRewrite, pszFileName,PVR_MAX_FILEPATH_LEN);
 
                                if(strlen(szFileNameRewrite) == PVR_MAX_FILEPATH_LEN-1) {
@@ -335,7 +410,7 @@ IMG_VOID PVRSRVDebugPrintf  (
                                while(*pszTruncIter++ != 0)
                                {
                                        IMG_CHAR* pszNextStartPoint;
-                                       
+                                       /* Find '/../' pattern */
                                        if(
                                           !( ( *pszTruncIter == '/' && (pszTruncIter-4 >= szFileNameRewrite) ) &&
                                                 ( *(pszTruncIter-1) == '.') &&
@@ -343,7 +418,7 @@ IMG_VOID PVRSRVDebugPrintf  (
                                                 ( *(pszTruncIter-3) == '/') )
                                           ) continue;
 
-                                       
+                                       /* Find previous '/' */
                                        pszTruncBackInter = pszTruncIter - 3;
                                        while(*(--pszTruncBackInter) != '/')
                                        {
@@ -351,19 +426,19 @@ IMG_VOID PVRSRVDebugPrintf        (
                                        }
                                        pszNextStartPoint = pszTruncBackInter;
 
-                                       
+                                       /* Remove found region */
                                        while(*pszTruncIter != 0)
                                        {
                                                *pszTruncBackInter++ = *pszTruncIter++;
                                        }
                                        *pszTruncBackInter = 0;
 
-                                       
+                                       /* Start again */
                                        pszTruncIter = pszNextStartPoint;
                                }
 
                                pszFileName = szFileNameRewrite;
-                               
+                               /* Remove first '/' if exist (it's always relative path */
                                if(*pszFileName == '/') pszFileName++;
 #endif
 
@@ -374,7 +449,7 @@ IMG_VOID PVRSRVDebugPrintf  (
                                {
                                        pszFileName = pszLeafName;
                        }
-#endif 
+#endif /* __sh__ */
 
                                if (BAppend(pszBuf, ui32BufSiz, " [%u, %s]", ui32Line, pszFileName))
                                {
@@ -397,16 +472,16 @@ IMG_VOID PVRSRVDebugPrintf        (
        }
 }
 
-#endif 
+#endif /* PVRSRV_NEED_PVR_DPF */
 
 #if defined(DEBUG)
 
 IMG_INT PVRDebugProcSetLevel(struct file *file, const IMG_CHAR *buffer, IMG_UINT32 count, IMG_VOID *data)
 {
-#define        _PROC_SET_BUFFER_SZ             2
+#define        _PROC_SET_BUFFER_SZ             6
        IMG_CHAR data_buffer[_PROC_SET_BUFFER_SZ];
 
-       if (count != _PROC_SET_BUFFER_SZ)
+       if (count > _PROC_SET_BUFFER_SZ)
        {
                return -EINVAL;
        }
@@ -416,7 +491,9 @@ IMG_INT PVRDebugProcSetLevel(struct file *file, const IMG_CHAR *buffer, IMG_UINT
                        return -EINVAL;
                if (data_buffer[count - 1] != '\n')
                        return -EINVAL;
-               gPVRDebugLevel = data_buffer[0] - '0';
+               if (sscanf(data_buffer, "%i", &gPVRDebugLevel) == 0)
+                       return -EINVAL;
+               gPVRDebugLevel &= (1 << DBGPRIV_DBGLEVEL_COUNT) - 1;
        }
        return (count);
 }
@@ -426,4 +503,4 @@ void ProcSeqShowDebugLevel(struct seq_file *sfile,void* el)
        seq_printf(sfile, "%u\n", gPVRDebugLevel);
 }
 
-#endif 
+#endif /* defined(DEBUG) */
index 5528070..28b814f 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          PowerVR drm driver
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    linux module setup
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #if defined(SUPPORT_DRI_DRM)
 
 #include <linux/version.h>
 #include "pvr_drm_mod.h"
 #endif
 
+#if defined(NO_HARDWARE)
+#define PVR_DRM_NAME   SYS_SGX_DEV_NAME
+#else
 #define PVR_DRM_NAME   PVRSRV_MODNAME
+#endif
+
 #define PVR_DRM_DESC   "Imagination Technologies PVR DRM"
 
+#define        PVR_DRM_DATE    "20110701"
+
+#if defined(PVR_DRI_DRM_PLATFORM_DEV) && !defined(SUPPORT_DRI_DRM_PLUGIN)
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39))
+#define PVR_NEW_STYLE_DRM_PLATFORM_DEV
+#else
+#define PVR_OLD_STYLE_DRM_PLATFORM_DEV
+#endif
+#endif
+
+/*
+ * Prior to Linux 2.6.36, we couldn't do the release processing in post close
+ * when workqueues were being used, because drm_release held the big kernel
+ * lock (BKL) when it called post close.
+ * If the resman needs to wait for processing being done by a workqueue,
+ * that processing won't complete whilst the lock is held by another thread,
+ * as the workqueue won't get scheduled.
+ */
+#undef PVR_DRI_DRM_USE_POST_CLOSE
+#if (defined(SUPPORT_DRI_DRM_EXT) && !defined(PVR_LINUX_USING_WORKQUEUES)) || \
+       (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36))
+#define        PVR_DRI_DRM_USE_POST_CLOSE
+#endif
+
 DECLARE_WAIT_QUEUE_HEAD(sWaitForInit);
 
+#if defined(SUPPORT_DRM_MODESET)
+static struct drm_driver sPVRDrmDriver;
+#endif
+
+/* Once bInitComplete and bInitFailed are set, they stay set */
 IMG_BOOL bInitComplete;
 IMG_BOOL bInitFailed;
 
-#if !defined(PVR_DRI_DRM_NOT_PCI)
+#if !defined(PVR_DRI_DRM_NOT_PCI) && !defined(SUPPORT_DRI_DRM_PLUGIN)
 #if defined(PVR_DRI_DRM_PLATFORM_DEV)
 struct platform_device *gpsPVRLDMDev;
 #else
@@ -94,28 +143,28 @@ struct drm_device *gpsPVRDRMDev;
 
 #define PVR_DRM_FILE struct drm_file *
 
-#if !defined(SUPPORT_DRI_DRM_EXT)
+#if !defined(SUPPORT_DRI_DRM_EXT) && !defined(SUPPORT_DRI_DRM_PLUGIN)
 #if defined(PVR_DRI_DRM_PLATFORM_DEV)
-#if defined(PVR_LDM_PLATFORM_PRE_REGISTERED)
+#if defined(PVR_LDM_PLATFORM_PRE_REGISTERED) || defined(NO_HARDWARE)
 static struct platform_device_id asPlatIdList[] = {
        {SYS_SGX_DEV_NAME, 0},
        {}
 };
 #endif
-#else  
+#else  /* defined(PVR_DRI_DRM_PLATFORM_DEV) */
 static struct pci_device_id asPciIdList[] = {
 #if defined(PVR_DRI_DRM_NOT_PCI)
        {1, 1, 1, 1, 0, 0, 0},
-#else  
+#else  /* defined(PVR_DRI_DRM_NOT_PCI) */
        {SYS_SGX_DEV_VENDOR_ID, SYS_SGX_DEV_DEVICE_ID, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
 #if defined(SYS_SGX_DEV1_DEVICE_ID)
        {SYS_SGX_DEV_VENDOR_ID, SYS_SGX_DEV1_DEVICE_ID, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
-#endif 
-#endif 
+#endif /* defined(SYS_SGX_DEV1_DEVICE_ID) */
+#endif /* defined(PVR_DRI_DRM_NOT_PCI) */
        {0}
 };
-#endif 
-#endif 
+#endif /* defined(PVR_DRI_DRM_PLATFORM_DEV) */
+#endif /* !defined(SUPPORT_DRI_DRM_EXT) */
 
 DRI_DRM_STATIC int
 PVRSRVDrmLoad(struct drm_device *dev, unsigned long flags)
@@ -125,7 +174,7 @@ PVRSRVDrmLoad(struct drm_device *dev, unsigned long flags)
        PVR_TRACE(("PVRSRVDrmLoad"));
 
        gpsPVRDRMDev = dev;
-#if !defined(PVR_DRI_DRM_NOT_PCI)
+#if !defined(PVR_DRI_DRM_NOT_PCI) && !defined(SUPPORT_DRI_DRM_PLUGIN)
 #if defined(PVR_DRI_DRM_PLATFORM_DEV)
        gpsPVRLDMDev = dev->platformdev;
 #else
@@ -140,7 +189,7 @@ PVRSRVDrmLoad(struct drm_device *dev, unsigned long flags)
                goto exit;
        }
 #endif
-       
+       /* Module initialisation */
        iRes = PVRCore_Init();
        if (iRes != 0)
        {
@@ -227,13 +276,22 @@ PVRSRVDrmOpen(struct drm_device *dev, struct drm_file *file)
        return PVRSRVOpen(dev, file);
 }
 
-#if defined(SUPPORT_DRI_DRM_EXT) && !defined(PVR_LINUX_USING_WORKQUEUES)
+#if defined(PVR_DRI_DRM_USE_POST_CLOSE) || defined(SUPPORT_DRI_DRM_PLUGIN)
+#if defined(SUPPORT_DRI_DRM_PLUGIN)
+DRI_DRM_STATIC int
+PVRSRVDrmRelease(struct drm_device *dev, struct drm_file *file)
+#else
 DRI_DRM_STATIC void
 PVRSRVDrmPostClose(struct drm_device *dev, struct drm_file *file)
+#endif
 {
        PVRSRVRelease(file->driver_priv);
 
        file->driver_priv = NULL;
+
+#if defined(SUPPORT_DRI_DRM_PLUGIN)
+       return 0;
+#endif
 }
 #else
 DRI_DRM_STATIC int
@@ -247,7 +305,10 @@ PVRSRVDrmRelease(struct inode *inode, struct file *filp)
 
        if (ret != 0)
        {
-               
+               /*
+                * An error means drm_release didn't call drm_lastclose,
+                * but it will have freed file_priv.
+                */
                PVR_DPF((PVR_DBG_ERROR, "%s : drm_release failed: %d",
                        __FUNCTION__, ret));
        }
@@ -322,6 +383,34 @@ PVRDRM_Display_ioctl(struct drm_device *dev, void *arg, struct drm_file *pFile)
 }
 #endif
 
+#if defined(SUPPORT_DRM_MODESET)
+static int
+PVRSRVPciProbe(struct pci_dev *dev, const struct pci_device_id *id)
+{
+       PVR_TRACE(("PVRSRVPciProbe"));
+
+       return drm_get_dev(dev, id, &sPVRDrmDriver);
+}
+
+static void
+PVRSRVPciRemove(struct pci_dev *dev)
+{
+       struct drm_device *psDrmDev;
+
+       PVR_TRACE(("PVRSRVPciRemove"));
+
+       psDrmDev = pci_get_drvdata(dev);
+       drm_put_dev(psDrmDev);
+}
+#endif
+
+/*
+ * For Linux 2.6.33 and above, the DRM ioctl entry point is of the unlocked
+ * variety.  The big kernel lock is still taken for ioctls, unless
+ * the DRM_UNLOCKED flag is set.  If you revise one of the driver specific
+ * ioctls, or add a new one, consider whether the gPVRSRVLock mutex needs
+ * to be taken.
+ */
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,33))
 #define        PVR_DRM_FOPS_IOCTL      .unlocked_ioctl
 #define        PVR_DRM_UNLOCKED        DRM_UNLOCKED
@@ -350,16 +439,37 @@ struct drm_ioctl_desc sPVRDrmIoctls[] = {
 #endif
 };
 
+#if !defined(SUPPORT_DRI_DRM_PLUGIN)
 static int pvr_max_ioctl = DRM_ARRAY_SIZE(sPVRDrmIoctls);
+#endif
 
-#if defined(PVR_DRI_DRM_PLATFORM_DEV) && !defined(SUPPORT_DRI_DRM_EXT)
+#if defined(PVR_DRI_DRM_PLATFORM_DEV) && !defined(SUPPORT_DRI_DRM_EXT) && \
+       !defined(SUPPORT_DRI_DRM_PLUGIN)
 static int PVRSRVDrmProbe(struct platform_device *pDevice);
 static int PVRSRVDrmRemove(struct platform_device *pDevice);
-#endif 
+#endif /* defined(PVR_DRI_DRM_PLATFORM_DEV) && !defined(SUPPORT_DRI_DRM_EXT) */
+
+#if defined(SUPPORT_DRI_DRM_PLUGIN)
+static PVRSRV_DRM_PLUGIN sPVRDrmPlugin =
+{
+       .name = PVR_DRM_NAME,
 
+       .open = PVRSRVDrmOpen,
+       .load = PVRSRVDrmLoad,
+       .unload = PVRSRVDrmUnload,
+
+       .release = PVRSRVDrmRelease,
+
+       .mmap = PVRMMap,
+
+       .ioctls = sPVRDrmIoctls,
+       .num_ioctls = DRM_ARRAY_SIZE(sPVRDrmIoctls),
+       .ioctl_start = 0
+};
+#else  /* defined(SUPPORT_DRI_DRM_PLUGIN) */
 static struct drm_driver sPVRDrmDriver = 
 {
-#if defined(PVR_DRI_DRM_PLATFORM_DEV)
+#if defined(PVR_OLD_STYLE_DRM_PLATFORM_DEV)
        .driver_features = DRIVER_USE_PLATFORM_DEVICE,
 #else
        .driver_features = 0,
@@ -368,7 +478,10 @@ static struct drm_driver sPVRDrmDriver =
        .load = PVRSRVDrmLoad,
        .unload = PVRSRVDrmUnload,
        .open = PVRSRVDrmOpen,
-#if !defined(PVR_DRI_DRM_PLATFORM_DEV)
+#if defined(PVR_DRI_DRM_USE_POST_CLOSE)
+       .postclose = PVRSRVDrmPostClose,
+#endif
+#if !defined(PVR_DRI_DRM_PLATFORM_DEV) && !defined(SUPPORT_DRM_MODESET)
        .suspend = PVRSRVDriverSuspend,
        .resume = PVRSRVDriverResume,
 #endif
@@ -381,13 +494,18 @@ static struct drm_driver sPVRDrmDriver =
        {
                .owner = THIS_MODULE,
                .open = drm_open,
+#if defined(PVR_DRI_DRM_USE_POST_CLOSE)
+               .release = drm_release,
+#else
                .release = PVRSRVDrmRelease,
+#endif
                PVR_DRM_FOPS_IOCTL = drm_ioctl,
                .mmap = PVRMMap,
                .poll = drm_poll,
                .fasync = drm_fasync,
        },
-#if defined(PVR_DRI_DRM_PLATFORM_DEV)
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,39))
+#if defined(PVR_OLD_STYLE_DRM_PLATFORM_DEV)
        .platform_driver =
        {
                .id_table = asPlatIdList,
@@ -402,43 +520,85 @@ static struct drm_driver sPVRDrmDriver =
                .shutdown = PVRSRVDriverShutdown,
        },
 #else
-#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,38))
        .pci_driver = 
        {
                .name = PVR_DRM_NAME,
                .id_table = asPciIdList,
+#if defined(SUPPORT_DRM_MODESET)
+               .probe = PVRSRVPciProbe,
+               .remove = PVRSRVPciRemove,
+               .suspend = PVRSRVDriverSuspend,
+               .resume = PVRSRVDriverResume,
+#endif
        },
-#else
-        .kdriver =
-        {
-        PVR_DRM_NAME,
-        asPciIdList,
-        },
 #endif
 #endif
        .name = PVR_DRM_NAME,
        .desc = PVR_DRM_DESC,
-       .date = PVR_BUILD_DATE,
+       .date = PVR_DRM_DATE,
        .major = PVRVERSION_MAJ,
        .minor = PVRVERSION_MIN,
        .patchlevel = PVRVERSION_BUILD,
 };
 
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39))
-static struct pci_driver pci_pvr_driver = {
-        .name = PVR_DRM_NAME,
-        .id_table = asPciIdList,
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39)) && !defined(PVR_DRI_DRM_PLATFORM_DEV)
+static struct pci_driver sPVRPCIDriver =
+{
+               .name = PVR_DRM_NAME,
+               .id_table = asPciIdList,
+#if defined(SUPPORT_DRM_MODESET)
+               .probe = PVRSRVPciProbe,
+               .remove = PVRSRVPciRemove,
+#endif
+};
+#endif
+
+#if defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV)
+#if defined(NO_HARDWARE)
+static void PVRSRVDeviceRelease(struct device unref__ *pDevice)
+{
+}
+
+static struct platform_device sPVRPlatDevice = {
+       .name                   = PVR_DRM_NAME,
+       .id                     = -1,
+       .dev                    = {
+               .release        = PVRSRVDeviceRelease
+       }
+};
+#endif
+
+static struct platform_driver sPVRPlatDriver =
+{
+       .id_table = asPlatIdList,
+       .driver =
+       {
+               .name = PVR_DRM_NAME,
+       },
+       .probe = PVRSRVDrmProbe,
+       .remove = PVRSRVDrmRemove,
+       .suspend = PVRSRVDriverSuspend,
+       .resume = PVRSRVDriverResume,
+       .shutdown = PVRSRVDriverShutdown,
 };
 #endif
 
+#endif /* defined(SUPPORT_DRI_DRM_PLUGIN) */
 
-#if defined(PVR_DRI_DRM_PLATFORM_DEV) && !defined(SUPPORT_DRI_DRM_EXT)
+#if defined(PVR_DRI_DRM_PLATFORM_DEV) && !defined(SUPPORT_DRI_DRM_EXT) && \
+       !defined(SUPPORT_DRI_DRM_PLUGIN)
 static int
 PVRSRVDrmProbe(struct platform_device *pDevice)
 {
        PVR_TRACE(("PVRSRVDrmProbe"));
 
+#if defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV)
+       gpsPVRLDMDev = pDevice;
+
+       return drm_platform_init(&sPVRDrmDriver, gpsPVRLDMDev);
+#else
        return drm_get_platform_dev(pDevice, &sPVRDrmDriver);
+#endif
 }
 
 static int
@@ -446,20 +606,45 @@ PVRSRVDrmRemove(struct platform_device *pDevice)
 {
        PVR_TRACE(("PVRSRVDrmRemove"));
 
+#if defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV)
+       drm_platform_exit(&sPVRDrmDriver, gpsPVRLDMDev);
+#else
        drm_put_dev(gpsPVRDRMDev);
-
+#endif
        return 0;
 }
+#endif
 
-#endif 
 static int __init PVRSRVDrmInit(void)
 {
        int iRes;
+#if !defined(SUPPORT_DRI_DRM_PLUGIN)
        sPVRDrmDriver.num_ioctls = pvr_max_ioctl;
+#endif
 
-       
+#if defined(SUPPORT_DRM_MODESET)
+       sPVRDrmDriver.driver_features |= DRIVER_MODESET;
+#endif
+
+       /* Must come before attempting to print anything via Services */
        PVRDPFInit();
 
+#if defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV)
+       iRes = platform_driver_register(&sPVRPlatDriver);
+#if defined(NO_HARDWARE)
+       if (iRes == 0)
+       {
+               iRes = platform_device_register(&sPVRPlatDevice);
+               if (iRes != 0)
+               {
+                       platform_driver_unregister(&sPVRPlatDriver);
+               }
+       }
+#endif
+#else  /* defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV) */
+#if defined(SUPPORT_DRI_DRM_PLUGIN)
+       iRes = SysDRMRegisterPlugin(&sPVRDrmPlugin);
+#else  /* defined(SUPPORT_DRI_DRM_PLUGIN) */
 #if defined(PVR_DRI_DRM_NOT_PCI)
        iRes = drm_pvr_dev_add();
        if (iRes != 0)
@@ -467,36 +652,65 @@ static int __init PVRSRVDrmInit(void)
                return iRes;
        }
 #endif
-#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,38))
-        iRes = drm_init(&sPVRDrmDriver);
+
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39))
+#if defined(PVR_DRI_DRM_PLATFORM_DEV)
+       iRes = drm_platform_init(&sPVRDrmDriver, gpsPVRLDMDev);
 #else
-        iRes = drm_pci_init(&sPVRDrmDriver,&pci_pvr_driver);
+       iRes = drm_pci_init(&sPVRDrmDriver, &sPVRPCIDriver);
 #endif
+#else  /* (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39)) */
+       iRes = drm_init(&sPVRDrmDriver);
+#endif /* (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39)) */
+
 #if defined(PVR_DRI_DRM_NOT_PCI)
        if (iRes != 0)
        {
                drm_pvr_dev_remove();
        }
 #endif
+#endif /* defined(SUPPORT_DRI_DRM_PLUGIN) */
+#endif /* defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV) */
        return iRes;
 }
        
 static void __exit PVRSRVDrmExit(void)
 {
-#if (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,38))
-        drm_exit(&sPVRDrmDriver);
+#if defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV)
+#if defined(NO_HARDWARE)
+       platform_device_unregister(&sPVRPlatDevice);
+#endif
+       platform_driver_unregister(&sPVRPlatDriver);
+#else  /* defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV) */
+#if defined(SUPPORT_DRI_DRM_PLUGIN)
+       SysDRMUnregisterPlugin(&sPVRDrmPlugin);
+#else  /* defined(SUPPORT_DRI_DRM_PLUGIN) */
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39))
+#if defined(PVR_DRI_DRM_PLATFORM_DEV)
+       drm_platform_exit(&sPVRDrmDriver, gpsPVRLDMDev);
 #else
-        drm_pci_exit(&sPVRDrmDriver,&pci_pvr_driver);
+       drm_pci_exit(&sPVRDrmDriver, &sPVRPCIDriver);
 #endif
+#else  /* (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39)) */
+       drm_exit(&sPVRDrmDriver);
+#endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,39)) */
 
 #if defined(PVR_DRI_DRM_NOT_PCI)
        drm_pvr_dev_remove();
 #endif
+#endif /* defined(SUPPORT_DRI_DRM_PLUGIN) */
+#endif /* defined(PVR_NEW_STYLE_DRM_PLATFORM_DEV) */
 }
 
+/*
+ * These macro calls define the initialisation and removal functions of the
+ * driver.  Although they are prefixed `module_', they apply when compiling
+ * statically as well; in both cases they define the function the kernel will
+ * run to start/stop the driver.
+*/
 module_init(PVRSRVDrmInit);
 module_exit(PVRSRVDrmExit);
-#endif 
-#endif 
+#endif /* !defined(SUPPORT_DRI_DRM_EXT) */
+#endif /* defined(SUPPORT_DRI_DRM) */
 
 
index 9bd5540..62488d0 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          PowerVR drm driver
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    drm module 
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #if !defined(__PVR_DRM_H__)
 #define __PVR_DRM_H__
 
@@ -42,19 +57,27 @@ void PVRCore_Cleanup(void);
 int PVRSRVOpen(struct drm_device *dev, struct drm_file *pFile);
 void PVRSRVRelease(void *pvPrivData);
 
+#if !defined(SUPPORT_DRI_DRM_PLUGIN)
 #if defined(PVR_DRI_DRM_PLATFORM_DEV)
 void PVRSRVDriverShutdown(LDM_DEV *pDevice);
 int PVRSRVDriverSuspend(LDM_DEV *pDevice, pm_message_t state);
 int PVRSRVDriverResume(LDM_DEV *pDevice);
 #else
+#if defined(SUPPORT_DRM_MODESET)
+int PVRSRVDriverSuspend(struct pci_dev *pDevice, pm_message_t state);
+int PVRSRVDriverResume(struct pci_dev *pDevice);
+#else
 int PVRSRVDriverSuspend(struct drm_device *pDevice, pm_message_t state);
 int PVRSRVDriverResume(struct drm_device *pDevice);
-#endif
+#endif /* defined(SUPPORT_DRM_MODESET) */
+#endif /* defined(PVR_DRI_DRM_PLATFORM_DEV) */
+#endif /* !defined(SUPPORT_DRI_DRM_PLUGIN) */
 
 int PVRSRV_BridgeDispatchKM(struct drm_device *dev, void *arg, struct drm_file *pFile);
 
 #if defined(SUPPORT_DRI_DRM_EXT)
 #define        DRI_DRM_STATIC
+/*Exported functions to common drm layer*/
 int PVRSRVDrmLoad(struct drm_device *dev, unsigned long flags);
 int PVRSRVDrmUnload(struct drm_device *dev);
 int PVRSRVDrmOpen(struct drm_device *dev, struct drm_file *file);
@@ -68,7 +91,7 @@ int PVRDRMUnprivCmd(struct drm_device *dev, IMG_VOID *arg, struct drm_file *pFil
 int PVRDRM_Dummy_ioctl(struct drm_device *dev, IMG_VOID *arg, struct drm_file *pFile);
 #else
 #define        DRI_DRM_STATIC  static
-#endif 
+#endif /* defined(SUPPORT_DRI_DRM_EXT) */
 
 #if defined(DISPLAY_CONTROLLER)
 extern int PVR_DRM_MAKENAME(DISPLAY_CONTROLLER, _Init)(struct drm_device *);
@@ -87,21 +110,51 @@ IMG_INT dbgdrv_ioctl(struct drm_device *dev, IMG_VOID *arg, struct drm_file *pFi
 #endif
 
 #if !defined(SUPPORT_DRI_DRM_EXT)
+/*
+ * We need the command number names to begin with "DRM_" for newer versions
+ * of the macro used to fill out the DRM ioctl table.  Similarly, the
+ * ioctl number names must begin with "DRM_IOCTL_". The suffixes for the
+ * two sets of strings must match (e.g. end with "PVR_SRVKM" in both
+ * cases).
+ */
+
 #define        DRM_PVR_SRVKM           PVR_DRM_SRVKM_CMD
 #define        DRM_PVR_IS_MASTER       PVR_DRM_IS_MASTER_CMD
 #define        DRM_PVR_UNPRIV          PVR_DRM_UNPRIV_CMD
 #define        DRM_PVR_DBGDRV          PVR_DRM_DBGDRV_CMD
 #define        DRM_PVR_DISP            PVR_DRM_DISP_CMD
 
+/* IOCTL numbers, relative to DRM_COMMAND_BASE */
 #define        DRM_IOCTL_PVR_SRVKM             _IO(0, DRM_PVR_SRVKM)
 #define        DRM_IOCTL_PVR_IS_MASTER         _IO(0, DRM_PVR_IS_MASTER)
 #define        DRM_IOCTL_PVR_UNPRIV            _IO(0, DRM_PVR_UNPRIV)
 #define        DRM_IOCTL_PVR_DBGDRV            _IO(0, DRM_PVR_DBGDRV)
 #define        DRM_IOCTL_PVR_DISP              _IO(0, DRM_PVR_DISP)
-#endif 
+#endif /* !defined(SUPPORT_DRI_DRM_EXT) */
+
+#if defined(SUPPORT_DRI_DRM_PLUGIN)
+typedef        struct {
+       char *name;
+
+       int (*load)(struct drm_device *dev, unsigned long flags);
+       int (*unload)(struct drm_device *dev);
+
+       int (*open)(struct drm_device *dev, struct drm_file *file);
+       int (*release)(struct drm_device *dev, struct drm_file *file);
+
+       int (*mmap)(struct file* pFile, struct vm_area_struct* ps_vma);
+
+       struct drm_ioctl_desc *ioctls;
+       int num_ioctls;
+       int ioctl_start;
+} PVRSRV_DRM_PLUGIN;
+
+int SysDRMRegisterPlugin(PVRSRV_DRM_PLUGIN *psDRMPlugin);
+void SysDRMUnregisterPlugin(PVRSRV_DRM_PLUGIN *psDRMPlugin);
+#endif /* defined(SUPPORT_DRI_DRM_PLUGIN) */
 
-#endif 
+#endif /* defined(SUPPORT_DRI_DRM) */
 
-#endif 
+#endif /* defined(__PVR_DRM_H__) */
 
 
index 6e7f1d3..7583d7e 100644 (file)
@@ -1,29 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Utility functions for user space access
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __PVR_UACCESS_H__
 #define __PVR_UACCESS_H__
 
@@ -53,7 +67,10 @@ static inline unsigned long pvr_copy_to_user(void __user *pvTo, const void *pvFr
 static inline unsigned long pvr_copy_from_user(void *pvTo, const void __user *pvFrom, unsigned long ulBytes)
 {
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,33))
-    
+    /*
+     * The compile time correctness checking introduced for copy_from_user in
+     * Linux 2.6.33 isn't fully comaptible with our usage of the function.
+     */
     if (access_ok(VERIFY_READ, pvFrom, ulBytes))
     {
        return __copy_from_user(pvTo, pvFrom, ulBytes);
@@ -67,5 +84,5 @@ static inline unsigned long pvr_copy_from_user(void *pvTo, const void __user *pv
 #define        pvr_put_user    put_user
 #define        pvr_get_user    get_user
 
-#endif 
+#endif /* __PVR_UACCESS_H__ */
 
index 3bbab7b..07a6412 100644 (file)
@@ -1,37 +1,54 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OCP HW definitions.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _OCPDEFS_H_
 #define _OCPDEFS_H_
 
+/* Register EUR_CR_OCP_REVISION */
 #define EUR_CR_OCP_REVISION                 0xFE00
 #define EUR_CR_OCP_REVISION_REV_MASK        0xFFFFFFFFUL
 #define EUR_CR_OCP_REVISION_REV_SHIFT       0
 #define EUR_CR_OCP_REVISION_REV_SIGNED      0
 
+/* Register EUR_CR_OCP_HWINFO */
 #define EUR_CR_OCP_HWINFO                   0xFE04
 #define EUR_CR_OCP_HWINFO_SYS_BUS_WIDTH_MASK 0x00000003UL
 #define EUR_CR_OCP_HWINFO_SYS_BUS_WIDTH_SHIFT 0
@@ -41,6 +58,7 @@
 #define EUR_CR_OCP_HWINFO_MEM_BUS_WIDTH_SHIFT 2
 #define EUR_CR_OCP_HWINFO_MEM_BUS_WIDTH_SIGNED 0
 
+/* Register EUR_CR_OCP_SYSCONFIG */
 #define EUR_CR_OCP_SYSCONFIG                0xFE10
 #define EUR_CR_OCP_SYSCONFIG_IDLE_MODE_MASK 0x0000000CUL
 #define EUR_CR_OCP_SYSCONFIG_IDLE_MODE_SHIFT 2
 #define EUR_CR_OCP_SYSCONFIG_STANDBY_MODE_SHIFT 4
 #define EUR_CR_OCP_SYSCONFIG_STANDBY_MODE_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQSTATUS_RAW_0 */
 #define EUR_CR_OCP_IRQSTATUS_RAW_0          0xFE24
 #define EUR_CR_OCP_IRQSTATUS_RAW_0_INIT_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQSTATUS_RAW_0_INIT_SHIFT 0
 #define EUR_CR_OCP_IRQSTATUS_RAW_0_INIT_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQSTATUS_RAW_1 */
 #define EUR_CR_OCP_IRQSTATUS_RAW_1          0xFE28
 #define EUR_CR_OCP_IRQSTATUS_RAW_1_TARGET_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQSTATUS_RAW_1_TARGET_SHIFT 0
 #define EUR_CR_OCP_IRQSTATUS_RAW_1_TARGET_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQSTATUS_RAW_2 */
 #define EUR_CR_OCP_IRQSTATUS_RAW_2          0xFE2C
 #define EUR_CR_OCP_IRQSTATUS_RAW_2_SGXCORE_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQSTATUS_RAW_2_SGXCORE_SHIFT 0
 #define EUR_CR_OCP_IRQSTATUS_RAW_2_SGXCORE_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQSTATUS_0 */
 #define EUR_CR_OCP_IRQSTATUS_0              0xFE30
 #define EUR_CR_OCP_IRQSTATUS_0_INIT_MASK    0x00000001UL
 #define EUR_CR_OCP_IRQSTATUS_0_INIT_SHIFT   0
 #define EUR_CR_OCP_IRQSTATUS_0_INIT_SIGNED  0
 
+/* Register EUR_CR_OCP_IRQSTATUS_1 */
 #define EUR_CR_OCP_IRQSTATUS_1              0xFE34
 #define EUR_CR_OCP_IRQSTATUS_1_TARGET_MASK  0x00000001UL
 #define EUR_CR_OCP_IRQSTATUS_1_TARGET_SHIFT 0
 #define EUR_CR_OCP_IRQSTATUS_1_TARGET_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQSTATUS_2 */
 #define EUR_CR_OCP_IRQSTATUS_2              0xFE38
 #define EUR_CR_OCP_IRQSTATUS_2_SGXCORE_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQSTATUS_2_SGXCORE_SHIFT 0
 #define EUR_CR_OCP_IRQSTATUS_2_SGXCORE_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQENABLE_SET_0 */
 #define EUR_CR_OCP_IRQENABLE_SET_0          0xFE3C
 #define EUR_CR_OCP_IRQENABLE_SET_0_INIT_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQENABLE_SET_0_INIT_SHIFT 0
 #define EUR_CR_OCP_IRQENABLE_SET_0_INIT_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQENABLE_SET_1 */
 #define EUR_CR_OCP_IRQENABLE_SET_1          0xFE40
 #define EUR_CR_OCP_IRQENABLE_SET_1_TARGET_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQENABLE_SET_1_TARGET_SHIFT 0
 #define EUR_CR_OCP_IRQENABLE_SET_1_TARGET_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQENABLE_SET_2 */
 #define EUR_CR_OCP_IRQENABLE_SET_2          0xFE44
 #define EUR_CR_OCP_IRQENABLE_SET_2_SGXCORE_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQENABLE_SET_2_SGXCORE_SHIFT 0
 #define EUR_CR_OCP_IRQENABLE_SET_2_SGXCORE_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQENABLE_CLR_0 */
 #define EUR_CR_OCP_IRQENABLE_CLR_0          0xFE48
 #define EUR_CR_OCP_IRQENABLE_CLR_0_INIT_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQENABLE_CLR_0_INIT_SHIFT 0
 #define EUR_CR_OCP_IRQENABLE_CLR_0_INIT_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQENABLE_CLR_1 */
 #define EUR_CR_OCP_IRQENABLE_CLR_1          0xFE4C
 #define EUR_CR_OCP_IRQENABLE_CLR_1_TARGET_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQENABLE_CLR_1_TARGET_SHIFT 0
 #define EUR_CR_OCP_IRQENABLE_CLR_1_TARGET_SIGNED 0
 
+/* Register EUR_CR_OCP_IRQENABLE_CLR_2 */
 #define EUR_CR_OCP_IRQENABLE_CLR_2          0xFE50
 #define EUR_CR_OCP_IRQENABLE_CLR_2_SGXCORE_MASK 0x00000001UL
 #define EUR_CR_OCP_IRQENABLE_CLR_2_SGXCORE_SHIFT 0
 #define EUR_CR_OCP_IRQENABLE_CLR_2_SGXCORE_SIGNED 0
 
+/* Register EUR_CR_OCP_PAGE_CONFIG */
 #define EUR_CR_OCP_PAGE_CONFIG              0xFF00
 #define EUR_CR_OCP_PAGE_CONFIG_MEM_PAGE_SIZE_MASK 0x00000001UL
 #define EUR_CR_OCP_PAGE_CONFIG_MEM_PAGE_SIZE_SHIFT 0
 #define EUR_CR_OCP_PAGE_CONFIG_SIZE_SHIFT   3
 #define EUR_CR_OCP_PAGE_CONFIG_SIZE_SIGNED  0
 
+/* Register EUR_CR_OCP_INTERRUPT_EVENT */
 #define EUR_CR_OCP_INTERRUPT_EVENT          0xFF04
 #define EUR_CR_OCP_INTERRUPT_EVENT_INIT_RESP_UNEXPECTED_MASK 0x00000001UL
 #define EUR_CR_OCP_INTERRUPT_EVENT_INIT_RESP_UNEXPECTED_SHIFT 0
 #define EUR_CR_OCP_INTERRUPT_EVENT_TARGET_INVALID_OCP_CMD_SHIFT 10
 #define EUR_CR_OCP_INTERRUPT_EVENT_TARGET_INVALID_OCP_CMD_SIGNED 0
 
+/* Register EUR_CR_OCP_DEBUG_CONFIG */
 #define EUR_CR_OCP_DEBUG_CONFIG             0xFF08
 #define EUR_CR_OCP_DEBUG_CONFIG_FORCE_TARGET_IDLE_MASK 0x00000003UL
 #define EUR_CR_OCP_DEBUG_CONFIG_FORCE_TARGET_IDLE_SHIFT 0
 #define EUR_CR_OCP_DEBUG_CONFIG_THALIA_INT_BYPASS_SHIFT 31
 #define EUR_CR_OCP_DEBUG_CONFIG_THALIA_INT_BYPASS_SIGNED 0
 
+/* Register EUR_CR_OCP_DEBUG_STATUS */
 #define EUR_CR_OCP_DEBUG_STATUS             0xFF0C
 #define EUR_CR_OCP_DEBUG_STATUS_TARGET_MCONNECT_MASK 0x00000003UL
 #define EUR_CR_OCP_DEBUG_STATUS_TARGET_MCONNECT_SHIFT 0
 #define EUR_CR_OCP_DEBUG_STATUS_CMD_DEBUG_STATE_SIGNED 0
 
 
-#endif 
+#endif /* _OCPDEFS_H_ */
 
+/*****************************************************************************
+ End of file (ocpdefs.h)
+*****************************************************************************/
index 810cb81..3223feb 100644 (file)
@@ -1,32 +1,48 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Hardware defs for SGX530.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _SGX530DEFS_KM_H_
 #define _SGX530DEFS_KM_H_
 
+/* Register EUR_CR_CLKGATECTL */
 #define EUR_CR_CLKGATECTL                   0x0000
 #define EUR_CR_CLKGATECTL_2D_CLKG_MASK      0x00000003U
 #define EUR_CR_CLKGATECTL_2D_CLKG_SHIFT     0
@@ -42,6 +58,7 @@
 #define EUR_CR_CLKGATECTL_USE_CLKG_SHIFT    20
 #define EUR_CR_CLKGATECTL_AUTO_MAN_REG_MASK 0x01000000U
 #define EUR_CR_CLKGATECTL_AUTO_MAN_REG_SHIFT 24
+/* Register EUR_CR_CLKGATESTATUS */
 #define EUR_CR_CLKGATESTATUS                0x0004
 #define EUR_CR_CLKGATESTATUS_2D_CLKS_MASK   0x00000001U
 #define EUR_CR_CLKGATESTATUS_2D_CLKS_SHIFT  0
@@ -55,6 +72,7 @@
 #define EUR_CR_CLKGATESTATUS_DPM_CLKS_SHIFT 16
 #define EUR_CR_CLKGATESTATUS_USE_CLKS_MASK  0x00100000U
 #define EUR_CR_CLKGATESTATUS_USE_CLKS_SHIFT 20
+/* Register EUR_CR_CLKGATECTLOVR */
 #define EUR_CR_CLKGATECTLOVR                0x0008
 #define EUR_CR_CLKGATECTLOVR_2D_CLKO_MASK   0x00000003U
 #define EUR_CR_CLKGATECTLOVR_2D_CLKO_SHIFT  0
 #define EUR_CR_CLKGATECTLOVR_DPM_CLKO_SHIFT 16
 #define EUR_CR_CLKGATECTLOVR_USE_CLKO_MASK  0x00300000U
 #define EUR_CR_CLKGATECTLOVR_USE_CLKO_SHIFT 20
+/* Register EUR_CR_CORE_ID */
 #define EUR_CR_CORE_ID                      0x0010
 #define EUR_CR_CORE_ID_CONFIG_MASK          0x0000FFFFU
 #define EUR_CR_CORE_ID_CONFIG_SHIFT         0
 #define EUR_CR_CORE_ID_ID_MASK              0xFFFF0000U
 #define EUR_CR_CORE_ID_ID_SHIFT             16
+/* Register EUR_CR_CORE_REVISION */
 #define EUR_CR_CORE_REVISION                0x0014
 #define EUR_CR_CORE_REVISION_MAINTENANCE_MASK 0x000000FFU
 #define EUR_CR_CORE_REVISION_MAINTENANCE_SHIFT 0
 #define EUR_CR_CORE_REVISION_MAJOR_SHIFT    16
 #define EUR_CR_CORE_REVISION_DESIGNER_MASK  0xFF000000U
 #define EUR_CR_CORE_REVISION_DESIGNER_SHIFT 24
+/* Register EUR_CR_DESIGNER_REV_FIELD1 */
 #define EUR_CR_DESIGNER_REV_FIELD1          0x0018
 #define EUR_CR_DESIGNER_REV_FIELD1_DESIGNER_REV_FIELD1_MASK 0xFFFFFFFFU
 #define EUR_CR_DESIGNER_REV_FIELD1_DESIGNER_REV_FIELD1_SHIFT 0
+/* Register EUR_CR_DESIGNER_REV_FIELD2 */
 #define EUR_CR_DESIGNER_REV_FIELD2          0x001C
 #define EUR_CR_DESIGNER_REV_FIELD2_DESIGNER_REV_FIELD2_MASK 0xFFFFFFFFU
 #define EUR_CR_DESIGNER_REV_FIELD2_DESIGNER_REV_FIELD2_SHIFT 0
+/* Register EUR_CR_SOFT_RESET */
 #define EUR_CR_SOFT_RESET                   0x0080
 #define EUR_CR_SOFT_RESET_BIF_RESET_MASK    0x00000001U
 #define EUR_CR_SOFT_RESET_BIF_RESET_SHIFT   0
 #define EUR_CR_SOFT_RESET_ISP_RESET_SHIFT   5
 #define EUR_CR_SOFT_RESET_TSP_RESET_MASK    0x00000040U
 #define EUR_CR_SOFT_RESET_TSP_RESET_SHIFT   6
+/* Register EUR_CR_EVENT_HOST_ENABLE2 */
 #define EUR_CR_EVENT_HOST_ENABLE2           0x0110
 #define EUR_CR_EVENT_HOST_ENABLE2_TRIG_TA_MASK 0x00000010U
 #define EUR_CR_EVENT_HOST_ENABLE2_TRIG_TA_SHIFT 4
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_3D_FREE_LOAD_SHIFT 1
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_TA_FREE_LOAD_SHIFT 0
+/* Register EUR_CR_EVENT_HOST_CLEAR2 */
 #define EUR_CR_EVENT_HOST_CLEAR2            0x0114
 #define EUR_CR_EVENT_HOST_CLEAR2_TRIG_TA_MASK 0x00000010U
 #define EUR_CR_EVENT_HOST_CLEAR2_TRIG_TA_SHIFT 4
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_3D_FREE_LOAD_SHIFT 1
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_TA_FREE_LOAD_SHIFT 0
+/* Register EUR_CR_EVENT_STATUS2 */
 #define EUR_CR_EVENT_STATUS2                0x0118
 #define EUR_CR_EVENT_STATUS2_TRIG_TA_MASK   0x00000010U
 #define EUR_CR_EVENT_STATUS2_TRIG_TA_SHIFT  4
 #define EUR_CR_EVENT_STATUS2_DPM_3D_FREE_LOAD_SHIFT 1
 #define EUR_CR_EVENT_STATUS2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_STATUS2_DPM_TA_FREE_LOAD_SHIFT 0
+/* Register EUR_CR_EVENT_STATUS */
 #define EUR_CR_EVENT_STATUS                 0x012CU
 #define EUR_CR_EVENT_STATUS_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_STATUS_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_STATUS_DPM_OUT_OF_MEMORY_MT_SHIFT 1
 #define EUR_CR_EVENT_STATUS_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_STATUS_DPM_3D_MEM_FREE_SHIFT 0
+/* Register EUR_CR_EVENT_HOST_ENABLE */
 #define EUR_CR_EVENT_HOST_ENABLE            0x0130
 #define EUR_CR_EVENT_HOST_ENABLE_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_HOST_ENABLE_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_OUT_OF_MEMORY_MT_SHIFT 1
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_3D_MEM_FREE_SHIFT 0
+/* Register EUR_CR_EVENT_HOST_CLEAR */
 #define EUR_CR_EVENT_HOST_CLEAR             0x0134
 #define EUR_CR_EVENT_HOST_CLEAR_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_HOST_CLEAR_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_OUT_OF_MEMORY_MT_SHIFT 1
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_3D_MEM_FREE_SHIFT 0
+/* Register EUR_CR_PDS_EXEC_BASE */
 #define EUR_CR_PDS_EXEC_BASE                0x0AB8
 #define EUR_CR_PDS_EXEC_BASE_ADDR_MASK      0x0FF00000U
 #define EUR_CR_PDS_EXEC_BASE_ADDR_SHIFT     20
+/* Register EUR_CR_EVENT_KICKER */
 #define EUR_CR_EVENT_KICKER                 0x0AC4
 #define EUR_CR_EVENT_KICKER_ADDRESS_MASK    0x0FFFFFF0U
 #define EUR_CR_EVENT_KICKER_ADDRESS_SHIFT   4
+/* Register EUR_CR_EVENT_KICK */
 #define EUR_CR_EVENT_KICK                   0x0AC8
 #define EUR_CR_EVENT_KICK_NOW_MASK          0x00000001U
 #define EUR_CR_EVENT_KICK_NOW_SHIFT         0
+/* Register EUR_CR_EVENT_TIMER */
 #define EUR_CR_EVENT_TIMER                  0x0ACC
 #define EUR_CR_EVENT_TIMER_ENABLE_MASK      0x01000000U
 #define EUR_CR_EVENT_TIMER_ENABLE_SHIFT     24
 #define EUR_CR_EVENT_TIMER_VALUE_MASK       0x00FFFFFFU
 #define EUR_CR_EVENT_TIMER_VALUE_SHIFT      0
+/* Register EUR_CR_PDS_INV0 */
 #define EUR_CR_PDS_INV0                     0x0AD0
 #define EUR_CR_PDS_INV0_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV0_DSC_SHIFT           0
+/* Register EUR_CR_PDS_INV1 */
 #define EUR_CR_PDS_INV1                     0x0AD4
 #define EUR_CR_PDS_INV1_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV1_DSC_SHIFT           0
+/* Register EUR_CR_PDS_INV2 */
 #define EUR_CR_PDS_INV2                     0x0AD8
 #define EUR_CR_PDS_INV2_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV2_DSC_SHIFT           0
+/* Register EUR_CR_PDS_INV3 */
 #define EUR_CR_PDS_INV3                     0x0ADC
 #define EUR_CR_PDS_INV3_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV3_DSC_SHIFT           0
+/* Register EUR_CR_PDS_INV_CSC */
 #define EUR_CR_PDS_INV_CSC                  0x0AE0
 #define EUR_CR_PDS_INV_CSC_KICK_MASK        0x00000001U
 #define EUR_CR_PDS_INV_CSC_KICK_SHIFT       0
+/* Register EUR_CR_PDS_PC_BASE */
 #define EUR_CR_PDS_PC_BASE                  0x0B2C
 #define EUR_CR_PDS_PC_BASE_ADDRESS_MASK     0x3FFFFFFFU
 #define EUR_CR_PDS_PC_BASE_ADDRESS_SHIFT    0
+/* Register EUR_CR_BIF_CTRL */
 #define EUR_CR_BIF_CTRL                     0x0C00
 #define EUR_CR_BIF_CTRL_NOREORDER_MASK      0x00000001U
 #define EUR_CR_BIF_CTRL_NOREORDER_SHIFT     0
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_ISP_SHIFT 14
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_USE_MASK 0x00008000U
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_USE_SHIFT 15
+/* Register EUR_CR_BIF_INT_STAT */
 #define EUR_CR_BIF_INT_STAT                 0x0C04
 #define EUR_CR_BIF_INT_STAT_FAULT_MASK      0x00003FFFU
 #define EUR_CR_BIF_INT_STAT_FAULT_SHIFT     0
 #define EUR_CR_BIF_INT_STAT_PF_N_RW_SHIFT   14
 #define EUR_CR_BIF_INT_STAT_FLUSH_COMPLETE_MASK 0x00008000U
 #define EUR_CR_BIF_INT_STAT_FLUSH_COMPLETE_SHIFT 15
+/* Register EUR_CR_BIF_FAULT */
 #define EUR_CR_BIF_FAULT                    0x0C08
 #define EUR_CR_BIF_FAULT_ADDR_MASK          0x0FFFF000U
 #define EUR_CR_BIF_FAULT_ADDR_SHIFT         12
+/* Register EUR_CR_BIF_DIR_LIST_BASE0 */
 #define EUR_CR_BIF_DIR_LIST_BASE0           0x0C84
 #define EUR_CR_BIF_DIR_LIST_BASE0_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE0_ADDR_SHIFT 12
+/* Register EUR_CR_BIF_TWOD_REQ_BASE */
 #define EUR_CR_BIF_TWOD_REQ_BASE            0x0C88
 #define EUR_CR_BIF_TWOD_REQ_BASE_ADDR_MASK  0x0FF00000U
 #define EUR_CR_BIF_TWOD_REQ_BASE_ADDR_SHIFT 20
+/* Register EUR_CR_BIF_TA_REQ_BASE */
 #define EUR_CR_BIF_TA_REQ_BASE              0x0C90
 #define EUR_CR_BIF_TA_REQ_BASE_ADDR_MASK    0x0FF00000U
 #define EUR_CR_BIF_TA_REQ_BASE_ADDR_SHIFT   20
+/* Register EUR_CR_BIF_MEM_REQ_STAT */
 #define EUR_CR_BIF_MEM_REQ_STAT             0x0CA8
 #define EUR_CR_BIF_MEM_REQ_STAT_READS_MASK  0x000000FFU
 #define EUR_CR_BIF_MEM_REQ_STAT_READS_SHIFT 0
+/* Register EUR_CR_BIF_3D_REQ_BASE */
 #define EUR_CR_BIF_3D_REQ_BASE              0x0CAC
 #define EUR_CR_BIF_3D_REQ_BASE_ADDR_MASK    0x0FF00000U
 #define EUR_CR_BIF_3D_REQ_BASE_ADDR_SHIFT   20
+/* Register EUR_CR_BIF_ZLS_REQ_BASE */
 #define EUR_CR_BIF_ZLS_REQ_BASE             0x0CB0
 #define EUR_CR_BIF_ZLS_REQ_BASE_ADDR_MASK   0x0FF00000U
 #define EUR_CR_BIF_ZLS_REQ_BASE_ADDR_SHIFT  20
+/* Register EUR_CR_2D_BLIT_STATUS */
 #define EUR_CR_2D_BLIT_STATUS               0x0E04
 #define EUR_CR_2D_BLIT_STATUS_COMPLETE_MASK 0x00FFFFFFU
 #define EUR_CR_2D_BLIT_STATUS_COMPLETE_SHIFT 0
 #define EUR_CR_2D_BLIT_STATUS_BUSY_MASK     0x01000000U
 #define EUR_CR_2D_BLIT_STATUS_BUSY_SHIFT    24
+/* Register EUR_CR_2D_VIRTUAL_FIFO_0 */
 #define EUR_CR_2D_VIRTUAL_FIFO_0            0x0E10
 #define EUR_CR_2D_VIRTUAL_FIFO_0_ENABLE_MASK 0x00000001U
 #define EUR_CR_2D_VIRTUAL_FIFO_0_ENABLE_SHIFT 0
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_DIV_SHIFT 4
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_MUL_MASK 0x0000F000U
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_MUL_SHIFT 12
+/* Register EUR_CR_2D_VIRTUAL_FIFO_1 */
 #define EUR_CR_2D_VIRTUAL_FIFO_1            0x0E14
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_ACC_MASK 0x00000FFFU
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_ACC_SHIFT 0
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MAX_ACC_SHIFT 12
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_METRIC_MASK 0xFF000000U
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_METRIC_SHIFT 24
+/* Table EUR_CR_USE_CODE_BASE */
+/* Register EUR_CR_USE_CODE_BASE */
 #define EUR_CR_USE_CODE_BASE(X)     (0x0A0C + (4 * (X)))
 #define EUR_CR_USE_CODE_BASE_ADDR_MASK      0x00FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_SHIFT     0
 #define EUR_CR_USE_CODE_BASE_DM_MASK        0x03000000U
 #define EUR_CR_USE_CODE_BASE_DM_SHIFT       24
+/* Number of entries in table EUR_CR_USE_CODE_BASE */
 #define EUR_CR_USE_CODE_BASE_SIZE_UINT32 16
 #define EUR_CR_USE_CODE_BASE_NUM_ENTRIES 16
 #define EUR_CR_MNE_CR_CTRL                                             0x0D00
 #define EUR_CR_MNE_CR_EVENT_CLEAR_INVAL_SHIFT  0
 #define EUR_CR_MNE_CR_CTRL_INVAL                               0x0D20
 
-#endif 
+#endif /* _SGX530DEFS_KM_H_ */
 
index c09aa26..47080c7 100644 (file)
@@ -1,32 +1,48 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Hardware defs for SGX540.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _SGX540DEFS_KM_H_
 #define _SGX540DEFS_KM_H_
 
+/* Register EUR_CR_CLKGATECTL */
 #define EUR_CR_CLKGATECTL                   0x0000
 #define EUR_CR_CLKGATECTL_ISP_CLKG_MASK     0x00000003U
 #define EUR_CR_CLKGATECTL_ISP_CLKG_SHIFT    0
@@ -52,6 +68,7 @@
 #define EUR_CR_CLKGATECTL_AUTO_MAN_REG_SHIFT 24
 #define EUR_CR_CLKGATECTL_SYSTEM_CLKG_MASK  0x10000000U
 #define EUR_CR_CLKGATECTL_SYSTEM_CLKG_SHIFT 28
+/* Register EUR_CR_CLKGATECTL2 */
 #define EUR_CR_CLKGATECTL2                  0x0004
 #define EUR_CR_CLKGATECTL2_PBE_CLKG_MASK    0x00000003U
 #define EUR_CR_CLKGATECTL2_PBE_CLKG_SHIFT   0
@@ -75,6 +92,7 @@
 #define EUR_CR_CLKGATECTL2_TEX1_CLKG_SHIFT  18
 #define EUR_CR_CLKGATECTL2_MADD1_CLKG_MASK  0x00300000U
 #define EUR_CR_CLKGATECTL2_MADD1_CLKG_SHIFT 20
+/* Register EUR_CR_CLKGATESTATUS */
 #define EUR_CR_CLKGATESTATUS                0x0008
 #define EUR_CR_CLKGATESTATUS_ISP_CLKS_MASK  0x00000001U
 #define EUR_CR_CLKGATESTATUS_ISP_CLKS_SHIFT 0
 #define EUR_CR_CLKGATESTATUS_IDXFIFO_CLKS_SHIFT 19
 #define EUR_CR_CLKGATESTATUS_TA_CLKS_MASK   0x00100000U
 #define EUR_CR_CLKGATESTATUS_TA_CLKS_SHIFT  20
+/* Register EUR_CR_CLKGATECTLOVR */
 #define EUR_CR_CLKGATECTLOVR                0x000C
 #define EUR_CR_CLKGATECTLOVR_ISP_CLKO_MASK  0x00000003U
 #define EUR_CR_CLKGATECTLOVR_ISP_CLKO_SHIFT 0
 #define EUR_CR_CLKGATECTLOVR_IDXFIFO_CLKO_SHIFT 16
 #define EUR_CR_CLKGATECTLOVR_TA_CLKO_MASK   0x000C0000U
 #define EUR_CR_CLKGATECTLOVR_TA_CLKO_SHIFT  18
+/* Register EUR_CR_POWER */
 #define EUR_CR_POWER                        0x001C
 #define EUR_CR_POWER_PIPE_DISABLE_MASK      0x00000001U
 #define EUR_CR_POWER_PIPE_DISABLE_SHIFT     0
+/* Register EUR_CR_CORE_ID */
 #define EUR_CR_CORE_ID                      0x0020
 #define EUR_CR_CORE_ID_CONFIG_MASK          0x0000FFFFU
 #define EUR_CR_CORE_ID_CONFIG_SHIFT         0
 #define EUR_CR_CORE_ID_ID_MASK              0xFFFF0000U
 #define EUR_CR_CORE_ID_ID_SHIFT             16
+/* Register EUR_CR_CORE_REVISION */
 #define EUR_CR_CORE_REVISION                0x0024
 #define EUR_CR_CORE_REVISION_MAINTENANCE_MASK 0x000000FFU
 #define EUR_CR_CORE_REVISION_MAINTENANCE_SHIFT 0
 #define EUR_CR_CORE_REVISION_MAJOR_SHIFT    16
 #define EUR_CR_CORE_REVISION_DESIGNER_MASK  0xFF000000U
 #define EUR_CR_CORE_REVISION_DESIGNER_SHIFT 24
+/* Register EUR_CR_DESIGNER_REV_FIELD1 */
 #define EUR_CR_DESIGNER_REV_FIELD1          0x0028
 #define EUR_CR_DESIGNER_REV_FIELD1_DESIGNER_REV_FIELD1_MASK 0xFFFFFFFFU
 #define EUR_CR_DESIGNER_REV_FIELD1_DESIGNER_REV_FIELD1_SHIFT 0
+/* Register EUR_CR_DESIGNER_REV_FIELD2 */
 #define EUR_CR_DESIGNER_REV_FIELD2          0x002C
 #define EUR_CR_DESIGNER_REV_FIELD2_DESIGNER_REV_FIELD2_MASK 0xFFFFFFFFU
 #define EUR_CR_DESIGNER_REV_FIELD2_DESIGNER_REV_FIELD2_SHIFT 0
+/* Register EUR_CR_SOFT_RESET */
 #define EUR_CR_SOFT_RESET                   0x0080
 #define EUR_CR_SOFT_RESET_BIF_RESET_MASK    0x00000001U
 #define EUR_CR_SOFT_RESET_BIF_RESET_SHIFT   0
 #define EUR_CR_SOFT_RESET_IDXFIFO_RESET_SHIFT 16
 #define EUR_CR_SOFT_RESET_TA_RESET_MASK     0x00020000U
 #define EUR_CR_SOFT_RESET_TA_RESET_SHIFT    17
+/* Register EUR_CR_EVENT_HOST_ENABLE2 */
 #define EUR_CR_EVENT_HOST_ENABLE2           0x0110
 #define EUR_CR_EVENT_HOST_ENABLE2_TRIG_TA_MASK 0x00000010U
 #define EUR_CR_EVENT_HOST_ENABLE2_TRIG_TA_SHIFT 4
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_3D_FREE_LOAD_SHIFT 1
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_TA_FREE_LOAD_SHIFT 0
+/* Register EUR_CR_EVENT_HOST_CLEAR2 */
 #define EUR_CR_EVENT_HOST_CLEAR2            0x0114
 #define EUR_CR_EVENT_HOST_CLEAR2_TRIG_TA_MASK 0x00000010U
 #define EUR_CR_EVENT_HOST_CLEAR2_TRIG_TA_SHIFT 4
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_3D_FREE_LOAD_SHIFT 1
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_TA_FREE_LOAD_SHIFT 0
+/* Register EUR_CR_EVENT_STATUS2 */
 #define EUR_CR_EVENT_STATUS2                0x0118
 #define EUR_CR_EVENT_STATUS2_TRIG_TA_MASK   0x00000010U
 #define EUR_CR_EVENT_STATUS2_TRIG_TA_SHIFT  4
 #define EUR_CR_EVENT_STATUS2_DPM_3D_FREE_LOAD_SHIFT 1
 #define EUR_CR_EVENT_STATUS2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_STATUS2_DPM_TA_FREE_LOAD_SHIFT 0
+/* Register EUR_CR_EVENT_STATUS */
 #define EUR_CR_EVENT_STATUS                 0x012CU
 #define EUR_CR_EVENT_STATUS_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_STATUS_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_STATUS_DPM_OUT_OF_MEMORY_MT_SHIFT 1
 #define EUR_CR_EVENT_STATUS_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_STATUS_DPM_3D_MEM_FREE_SHIFT 0
+/* Register EUR_CR_EVENT_HOST_ENABLE */
 #define EUR_CR_EVENT_HOST_ENABLE            0x0130
 #define EUR_CR_EVENT_HOST_ENABLE_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_HOST_ENABLE_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_OUT_OF_MEMORY_MT_SHIFT 1
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_3D_MEM_FREE_SHIFT 0
+/* Register EUR_CR_EVENT_HOST_CLEAR */
 #define EUR_CR_EVENT_HOST_CLEAR             0x0134
 #define EUR_CR_EVENT_HOST_CLEAR_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_HOST_CLEAR_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_OUT_OF_MEMORY_MT_SHIFT 1
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_3D_MEM_FREE_SHIFT 0
+/* Register EUR_CR_TIMER */
 #define EUR_CR_TIMER                        0x0144
 #define EUR_CR_TIMER_VALUE_MASK             0xFFFFFFFFU
 #define EUR_CR_TIMER_VALUE_SHIFT            0
+/* Register EUR_CR_EVENT_KICK1 */
 #define EUR_CR_EVENT_KICK1                  0x0AB0
 #define EUR_CR_EVENT_KICK1_NOW_MASK         0x000000FFU
 #define EUR_CR_EVENT_KICK1_NOW_SHIFT        0
+/* Register EUR_CR_PDS_EXEC_BASE */
 #define EUR_CR_PDS_EXEC_BASE                0x0AB8
 #define EUR_CR_PDS_EXEC_BASE_ADDR_MASK      0x0FF00000U
 #define EUR_CR_PDS_EXEC_BASE_ADDR_SHIFT     20
+/* Register EUR_CR_EVENT_KICK2 */
 #define EUR_CR_EVENT_KICK2                  0x0AC0
 #define EUR_CR_EVENT_KICK2_NOW_MASK         0x00000001U
 #define EUR_CR_EVENT_KICK2_NOW_SHIFT        0
+/* Register EUR_CR_EVENT_KICKER */
 #define EUR_CR_EVENT_KICKER                 0x0AC4
 #define EUR_CR_EVENT_KICKER_ADDRESS_MASK    0x0FFFFFF0U
 #define EUR_CR_EVENT_KICKER_ADDRESS_SHIFT   4
+/* Register EUR_CR_EVENT_KICK */
 #define EUR_CR_EVENT_KICK                   0x0AC8
 #define EUR_CR_EVENT_KICK_NOW_MASK          0x00000001U
 #define EUR_CR_EVENT_KICK_NOW_SHIFT         0
+/* Register EUR_CR_EVENT_TIMER */
 #define EUR_CR_EVENT_TIMER                  0x0ACC
 #define EUR_CR_EVENT_TIMER_ENABLE_MASK      0x01000000U
 #define EUR_CR_EVENT_TIMER_ENABLE_SHIFT     24
 #define EUR_CR_EVENT_TIMER_VALUE_MASK       0x00FFFFFFU
 #define EUR_CR_EVENT_TIMER_VALUE_SHIFT      0
+/* Register EUR_CR_PDS_INV0 */
 #define EUR_CR_PDS_INV0                     0x0AD0
 #define EUR_CR_PDS_INV0_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV0_DSC_SHIFT           0
+/* Register EUR_CR_PDS_INV1 */
 #define EUR_CR_PDS_INV1                     0x0AD4
 #define EUR_CR_PDS_INV1_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV1_DSC_SHIFT           0
+/* Register EUR_CR_EVENT_KICK3 */
 #define EUR_CR_EVENT_KICK3                  0x0AD8
 #define EUR_CR_EVENT_KICK3_NOW_MASK         0x00000001U
 #define EUR_CR_EVENT_KICK3_NOW_SHIFT        0
+/* Register EUR_CR_PDS_INV3 */
 #define EUR_CR_PDS_INV3                     0x0ADC
 #define EUR_CR_PDS_INV3_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV3_DSC_SHIFT           0
+/* Register EUR_CR_PDS_INV_CSC */
 #define EUR_CR_PDS_INV_CSC                  0x0AE0
 #define EUR_CR_PDS_INV_CSC_KICK_MASK        0x00000001U
 #define EUR_CR_PDS_INV_CSC_KICK_SHIFT       0
+/* Register EUR_CR_PDS_PC_BASE */
 #define EUR_CR_PDS_PC_BASE                  0x0B2C
 #define EUR_CR_PDS_PC_BASE_ADDRESS_MASK     0x00FFFFFFU
 #define EUR_CR_PDS_PC_BASE_ADDRESS_SHIFT    0
+/* Register EUR_CR_BIF_CTRL */
 #define EUR_CR_BIF_CTRL                     0x0C00
 #define EUR_CR_BIF_CTRL_NOREORDER_MASK      0x00000001U
 #define EUR_CR_BIF_CTRL_NOREORDER_SHIFT     0
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_ISP_SHIFT 14
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_USE_MASK 0x00008000U
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_USE_SHIFT 15
+/* Register EUR_CR_BIF_INT_STAT */
 #define EUR_CR_BIF_INT_STAT                 0x0C04
 #define EUR_CR_BIF_INT_STAT_FAULT_MASK      0x00003FFFU
 #define EUR_CR_BIF_INT_STAT_FAULT_SHIFT     0
 #define EUR_CR_BIF_INT_STAT_PF_N_RW_SHIFT   14
 #define EUR_CR_BIF_INT_STAT_FLUSH_COMPLETE_MASK 0x00008000U
 #define EUR_CR_BIF_INT_STAT_FLUSH_COMPLETE_SHIFT 15
+/* Register EUR_CR_BIF_FAULT */
 #define EUR_CR_BIF_FAULT                    0x0C08
 #define EUR_CR_BIF_FAULT_SB_MASK            0x000001F0U
 #define EUR_CR_BIF_FAULT_SB_SHIFT           4
 #define EUR_CR_BIF_FAULT_ADDR_MASK          0x0FFFF000U
 #define EUR_CR_BIF_FAULT_ADDR_SHIFT         12
+/* Register EUR_CR_BIF_DIR_LIST_BASE0 */
 #define EUR_CR_BIF_DIR_LIST_BASE0           0x0C84
 #define EUR_CR_BIF_DIR_LIST_BASE0_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE0_ADDR_SHIFT 12
+/* Register EUR_CR_BIF_TA_REQ_BASE */
 #define EUR_CR_BIF_TA_REQ_BASE              0x0C90
 #define EUR_CR_BIF_TA_REQ_BASE_ADDR_MASK    0x0FF00000U
 #define EUR_CR_BIF_TA_REQ_BASE_ADDR_SHIFT   20
+/* Register EUR_CR_BIF_MEM_REQ_STAT */
 #define EUR_CR_BIF_MEM_REQ_STAT             0x0CA8
 #define EUR_CR_BIF_MEM_REQ_STAT_READS_MASK  0x000000FFU
 #define EUR_CR_BIF_MEM_REQ_STAT_READS_SHIFT 0
+/* Register EUR_CR_BIF_3D_REQ_BASE */
 #define EUR_CR_BIF_3D_REQ_BASE              0x0CAC
 #define EUR_CR_BIF_3D_REQ_BASE_ADDR_MASK    0x0FF00000U
 #define EUR_CR_BIF_3D_REQ_BASE_ADDR_SHIFT   20
+/* Register EUR_CR_BIF_ZLS_REQ_BASE */
 #define EUR_CR_BIF_ZLS_REQ_BASE             0x0CB0
 #define EUR_CR_BIF_ZLS_REQ_BASE_ADDR_MASK   0x0FF00000U
 #define EUR_CR_BIF_ZLS_REQ_BASE_ADDR_SHIFT  20
+/* Register EUR_CR_2D_BLIT_STATUS */
 #define EUR_CR_2D_BLIT_STATUS               0x0E04
 #define EUR_CR_2D_BLIT_STATUS_COMPLETE_MASK 0x00FFFFFFU
 #define EUR_CR_2D_BLIT_STATUS_COMPLETE_SHIFT 0
 #define EUR_CR_2D_BLIT_STATUS_BUSY_MASK     0x01000000U
 #define EUR_CR_2D_BLIT_STATUS_BUSY_SHIFT    24
+/* Register EUR_CR_2D_VIRTUAL_FIFO_0 */
 #define EUR_CR_2D_VIRTUAL_FIFO_0            0x0E10
 #define EUR_CR_2D_VIRTUAL_FIFO_0_ENABLE_MASK 0x00000001U
 #define EUR_CR_2D_VIRTUAL_FIFO_0_ENABLE_SHIFT 0
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_DIV_SHIFT 4
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_MUL_MASK 0x0000F000U
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_MUL_SHIFT 12
+/* Register EUR_CR_2D_VIRTUAL_FIFO_1 */
 #define EUR_CR_2D_VIRTUAL_FIFO_1            0x0E14
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_ACC_MASK 0x00000FFFU
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_ACC_SHIFT 0
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MAX_ACC_SHIFT 12
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_METRIC_MASK 0xFF000000U
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_METRIC_SHIFT 24
+/* Table EUR_CR_USE_CODE_BASE */
+/* Register EUR_CR_USE_CODE_BASE */
 #define EUR_CR_USE_CODE_BASE(X)     (0x0A0C + (4 * (X)))
 #define EUR_CR_USE_CODE_BASE_ADDR_MASK      0x00FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_SHIFT     0
 #define EUR_CR_USE_CODE_BASE_DM_MASK        0x03000000U
 #define EUR_CR_USE_CODE_BASE_DM_SHIFT       24
+/* Number of entries in table EUR_CR_USE_CODE_BASE */
 #define EUR_CR_USE_CODE_BASE_SIZE_UINT32 16
 #define EUR_CR_USE_CODE_BASE_NUM_ENTRIES 16
 
-#endif 
+#endif /* _SGX540DEFS_KM_H_ */
 
index c18b8ad..79efcbc 100644 (file)
@@ -1,32 +1,48 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Hardware defs for SGX544.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _SGX544DEFS_KM_H_
 #define _SGX544DEFS_KM_H_
 
+/* Register EUR_CR_CLKGATECTL */
 #define EUR_CR_CLKGATECTL                   0x0000
 #define EUR_CR_CLKGATECTL_ISP_CLKG_MASK     0x00000003U
 #define EUR_CR_CLKGATECTL_ISP_CLKG_SHIFT    0
@@ -67,6 +83,7 @@
 #define EUR_CR_CLKGATECTL_SYSTEM_CLKG_MASK  0x10000000U
 #define EUR_CR_CLKGATECTL_SYSTEM_CLKG_SHIFT 28
 #define EUR_CR_CLKGATECTL_SYSTEM_CLKG_SIGNED 0
+/* Register EUR_CR_CLKGATECTL2 */
 #define EUR_CR_CLKGATECTL2                  0x0004
 #define EUR_CR_CLKGATECTL2_PBE_CLKG_MASK    0x00000003U
 #define EUR_CR_CLKGATECTL2_PBE_CLKG_SHIFT   0
 #define EUR_CR_CLKGATECTL2_DCU0_L0L1_CLKG_MASK 0x0C000000U
 #define EUR_CR_CLKGATECTL2_DCU0_L0L1_CLKG_SHIFT 26
 #define EUR_CR_CLKGATECTL2_DCU0_L0L1_CLKG_SIGNED 0
+/* Register EUR_CR_CLKGATESTATUS */
 #define EUR_CR_CLKGATESTATUS                0x0008
 #define EUR_CR_CLKGATESTATUS_ISP_CLKS_MASK  0x00000001U
 #define EUR_CR_CLKGATESTATUS_ISP_CLKS_SHIFT 0
 #define EUR_CR_CLKGATESTATUS_BIF_CORE_CLKS_MASK 0x01000000U
 #define EUR_CR_CLKGATESTATUS_BIF_CORE_CLKS_SHIFT 24
 #define EUR_CR_CLKGATESTATUS_BIF_CORE_CLKS_SIGNED 0
+/* Register EUR_CR_CLKGATECTLOVR */
 #define EUR_CR_CLKGATECTLOVR                0x000C
 #define EUR_CR_CLKGATECTLOVR_ISP_CLKO_MASK  0x00000003U
 #define EUR_CR_CLKGATECTLOVR_ISP_CLKO_SHIFT 0
 #define EUR_CR_CLKGATECTLOVR_BIF_CORE_CLKO_MASK 0x00300000U
 #define EUR_CR_CLKGATECTLOVR_BIF_CORE_CLKO_SHIFT 20
 #define EUR_CR_CLKGATECTLOVR_BIF_CORE_CLKO_SIGNED 0
+/* Register EUR_CR_POWER */
 #define EUR_CR_POWER                        0x001C
 #define EUR_CR_POWER_PIPE_DISABLE_MASK      0x00000001U
 #define EUR_CR_POWER_PIPE_DISABLE_SHIFT     0
 #define EUR_CR_POWER_PIPE_DISABLE_SIGNED    0
+/* Register EUR_CR_CORE_ID */
 #define EUR_CR_CORE_ID                      0x0020
 #define EUR_CR_CORE_ID_CONFIG_MULTI_MASK    0x00000001U
 #define EUR_CR_CORE_ID_CONFIG_MULTI_SHIFT   0
 #define EUR_CR_CORE_ID_ID_MASK              0xFFFF0000U
 #define EUR_CR_CORE_ID_ID_SHIFT             16
 #define EUR_CR_CORE_ID_ID_SIGNED            0
+/* Register EUR_CR_CORE_REVISION */
 #define EUR_CR_CORE_REVISION                0x0024
 #define EUR_CR_CORE_REVISION_MAINTENANCE_MASK 0x000000FFU
 #define EUR_CR_CORE_REVISION_MAINTENANCE_SHIFT 0
 #define EUR_CR_CORE_REVISION_DESIGNER_MASK  0xFF000000U
 #define EUR_CR_CORE_REVISION_DESIGNER_SHIFT 24
 #define EUR_CR_CORE_REVISION_DESIGNER_SIGNED 0
+/* Register EUR_CR_DESIGNER_REV_FIELD1 */
 #define EUR_CR_DESIGNER_REV_FIELD1          0x0028
 #define EUR_CR_DESIGNER_REV_FIELD1_DESIGNER_REV_FIELD1_MASK 0xFFFFFFFFU
 #define EUR_CR_DESIGNER_REV_FIELD1_DESIGNER_REV_FIELD1_SHIFT 0
 #define EUR_CR_DESIGNER_REV_FIELD1_DESIGNER_REV_FIELD1_SIGNED 0
+/* Register EUR_CR_DESIGNER_REV_FIELD2 */
 #define EUR_CR_DESIGNER_REV_FIELD2          0x002C
 #define EUR_CR_DESIGNER_REV_FIELD2_DESIGNER_REV_FIELD2_MASK 0xFFFFFFFFU
 #define EUR_CR_DESIGNER_REV_FIELD2_DESIGNER_REV_FIELD2_SHIFT 0
 #define EUR_CR_DESIGNER_REV_FIELD2_DESIGNER_REV_FIELD2_SIGNED 0
+/* Register EUR_CR_SOFT_RESET */
 #define EUR_CR_SOFT_RESET                   0x0080
 #define EUR_CR_SOFT_RESET_BIF_RESET_MASK    0x00000001U
 #define EUR_CR_SOFT_RESET_BIF_RESET_SHIFT   0
 #define EUR_CR_SOFT_RESET_DCU_L0L1_RESET_MASK 0x00080000U
 #define EUR_CR_SOFT_RESET_DCU_L0L1_RESET_SHIFT 19
 #define EUR_CR_SOFT_RESET_DCU_L0L1_RESET_SIGNED 0
+/* Register EUR_CR_EVENT_HOST_ENABLE2 */
 #define EUR_CR_EVENT_HOST_ENABLE2           0x0110
 #define EUR_CR_EVENT_HOST_ENABLE2_DATA_BREAKPOINT_UNTRAPPED_MASK 0x00000800U
 #define EUR_CR_EVENT_HOST_ENABLE2_DATA_BREAKPOINT_UNTRAPPED_SHIFT 11
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_TA_FREE_LOAD_SHIFT 0
 #define EUR_CR_EVENT_HOST_ENABLE2_DPM_TA_FREE_LOAD_SIGNED 0
+/* Register EUR_CR_EVENT_HOST_CLEAR2 */
 #define EUR_CR_EVENT_HOST_CLEAR2            0x0114
 #define EUR_CR_EVENT_HOST_CLEAR2_DATA_BREAKPOINT_UNTRAPPED_MASK 0x00000800U
 #define EUR_CR_EVENT_HOST_CLEAR2_DATA_BREAKPOINT_UNTRAPPED_SHIFT 11
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_TA_FREE_LOAD_SHIFT 0
 #define EUR_CR_EVENT_HOST_CLEAR2_DPM_TA_FREE_LOAD_SIGNED 0
+/* Register EUR_CR_EVENT_STATUS2 */
 #define EUR_CR_EVENT_STATUS2                0x0118
 #define EUR_CR_EVENT_STATUS2_DATA_BREAKPOINT_UNTRAPPED_MASK 0x00000800U
 #define EUR_CR_EVENT_STATUS2_DATA_BREAKPOINT_UNTRAPPED_SHIFT 11
 #define EUR_CR_EVENT_STATUS2_DPM_TA_FREE_LOAD_MASK 0x00000001U
 #define EUR_CR_EVENT_STATUS2_DPM_TA_FREE_LOAD_SHIFT 0
 #define EUR_CR_EVENT_STATUS2_DPM_TA_FREE_LOAD_SIGNED 0
+/* Register EUR_CR_EVENT_STATUS */
 #define EUR_CR_EVENT_STATUS                 0x012C
 #define EUR_CR_EVENT_STATUS_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_STATUS_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_STATUS_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_STATUS_DPM_3D_MEM_FREE_SHIFT 0
 #define EUR_CR_EVENT_STATUS_DPM_3D_MEM_FREE_SIGNED 0
+/* Register EUR_CR_EVENT_HOST_ENABLE */
 #define EUR_CR_EVENT_HOST_ENABLE            0x0130
 #define EUR_CR_EVENT_HOST_ENABLE_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_HOST_ENABLE_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_3D_MEM_FREE_SHIFT 0
 #define EUR_CR_EVENT_HOST_ENABLE_DPM_3D_MEM_FREE_SIGNED 0
+/* Register EUR_CR_EVENT_HOST_CLEAR */
 #define EUR_CR_EVENT_HOST_CLEAR             0x0134
 #define EUR_CR_EVENT_HOST_CLEAR_MASTER_INTERRUPT_MASK 0x80000000U
 #define EUR_CR_EVENT_HOST_CLEAR_MASTER_INTERRUPT_SHIFT 31
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_3D_MEM_FREE_MASK 0x00000001U
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_3D_MEM_FREE_SHIFT 0
 #define EUR_CR_EVENT_HOST_CLEAR_DPM_3D_MEM_FREE_SIGNED 0
+/* Register EUR_CR_TIMER */
 #define EUR_CR_TIMER                        0x0144
 #define EUR_CR_TIMER_VALUE_MASK             0xFFFFFFFFU
 #define EUR_CR_TIMER_VALUE_SHIFT            0
 #define EUR_CR_TIMER_VALUE_SIGNED           0
+/* Register EUR_CR_EVENT_KICK1 */
 #define EUR_CR_EVENT_KICK1                  0x0AB0
 #define EUR_CR_EVENT_KICK1_NOW_MASK         0x000000FFU
 #define EUR_CR_EVENT_KICK1_NOW_SHIFT        0
 #define EUR_CR_EVENT_KICK1_NOW_SIGNED       0
+/* Register EUR_CR_EVENT_KICK2 */
 #define EUR_CR_EVENT_KICK2                  0x0AC0
 #define EUR_CR_EVENT_KICK2_NOW_MASK         0x00000001U
 #define EUR_CR_EVENT_KICK2_NOW_SHIFT        0
 #define EUR_CR_EVENT_KICK2_NOW_SIGNED       0
+/* Register EUR_CR_EVENT_KICKER */
 #define EUR_CR_EVENT_KICKER                 0x0AC4
 #define EUR_CR_EVENT_KICKER_ADDRESS_MASK    0xFFFFFFF0U
 #define EUR_CR_EVENT_KICKER_ADDRESS_SHIFT   4
 #define EUR_CR_EVENT_KICKER_ADDRESS_SIGNED  0
+/* Register EUR_CR_EVENT_KICK */
 #define EUR_CR_EVENT_KICK                   0x0AC8
 #define EUR_CR_EVENT_KICK_NOW_MASK          0x00000001U
 #define EUR_CR_EVENT_KICK_NOW_SHIFT         0
 #define EUR_CR_EVENT_KICK_NOW_SIGNED        0
+/* Register EUR_CR_EVENT_TIMER */
 #define EUR_CR_EVENT_TIMER                  0x0ACC
 #define EUR_CR_EVENT_TIMER_ENABLE_MASK      0x01000000U
 #define EUR_CR_EVENT_TIMER_ENABLE_SHIFT     24
 #define EUR_CR_EVENT_TIMER_VALUE_MASK       0x00FFFFFFU
 #define EUR_CR_EVENT_TIMER_VALUE_SHIFT      0
 #define EUR_CR_EVENT_TIMER_VALUE_SIGNED     0
+/* Register EUR_CR_PDS_INV0 */
 #define EUR_CR_PDS_INV0                     0x0AD0
 #define EUR_CR_PDS_INV0_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV0_DSC_SHIFT           0
 #define EUR_CR_PDS_INV0_DSC_SIGNED          0
+/* Register EUR_CR_PDS_INV1 */
 #define EUR_CR_PDS_INV1                     0x0AD4
 #define EUR_CR_PDS_INV1_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV1_DSC_SHIFT           0
 #define EUR_CR_PDS_INV1_DSC_SIGNED          0
+/* Register EUR_CR_EVENT_KICK3 */
 #define EUR_CR_EVENT_KICK3                  0x0AD8
 #define EUR_CR_EVENT_KICK3_NOW_MASK         0x00000001U
 #define EUR_CR_EVENT_KICK3_NOW_SHIFT        0
 #define EUR_CR_EVENT_KICK3_NOW_SIGNED       0
+/* Register EUR_CR_PDS_INV3 */
 #define EUR_CR_PDS_INV3                     0x0ADC
 #define EUR_CR_PDS_INV3_DSC_MASK            0x00000001U
 #define EUR_CR_PDS_INV3_DSC_SHIFT           0
 #define EUR_CR_PDS_INV3_DSC_SIGNED          0
+/* Register EUR_CR_PDS_INV_CSC */
 #define EUR_CR_PDS_INV_CSC                  0x0AE0
 #define EUR_CR_PDS_INV_CSC_KICK_MASK        0x00000001U
 #define EUR_CR_PDS_INV_CSC_KICK_SHIFT       0
 #define EUR_CR_PDS_INV_CSC_KICK_SIGNED      0
+/* Register EUR_CR_BIF_CTRL */
 #define EUR_CR_BIF_CTRL                     0x0C00
 #define EUR_CR_BIF_CTRL_NOREORDER_MASK      0x00000001U
 #define EUR_CR_BIF_CTRL_NOREORDER_SHIFT     0
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_MASTER_DPM_MASK 0x00080000U
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_MASTER_DPM_SHIFT 19
 #define EUR_CR_BIF_CTRL_MMU_BYPASS_MASTER_DPM_SIGNED 0
+/* Register EUR_CR_BIF_INT_STAT */
 #define EUR_CR_BIF_INT_STAT                 0x0C04
 #define EUR_CR_BIF_INT_STAT_FAULT_REQ_MASK  0x00003FFFU
 #define EUR_CR_BIF_INT_STAT_FAULT_REQ_SHIFT 0
 #define EUR_CR_BIF_INT_STAT_FLUSH_COMPLETE_MASK 0x00080000U
 #define EUR_CR_BIF_INT_STAT_FLUSH_COMPLETE_SHIFT 19
 #define EUR_CR_BIF_INT_STAT_FLUSH_COMPLETE_SIGNED 0
+/* Register EUR_CR_BIF_FAULT */
 #define EUR_CR_BIF_FAULT                    0x0C08
 #define EUR_CR_BIF_FAULT_CID_MASK           0x0000000FU
 #define EUR_CR_BIF_FAULT_CID_SHIFT          0
 #define EUR_CR_BIF_FAULT_ADDR_MASK          0xFFFFF000U
 #define EUR_CR_BIF_FAULT_ADDR_SHIFT         12
 #define EUR_CR_BIF_FAULT_ADDR_SIGNED        0
+/* Register EUR_CR_BIF_TILE0 */
 #define EUR_CR_BIF_TILE0                    0x0C0C
 #define EUR_CR_BIF_TILE0_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE0_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE0_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE0_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE0_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE1 */
 #define EUR_CR_BIF_TILE1                    0x0C10
 #define EUR_CR_BIF_TILE1_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE1_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE1_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE1_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE1_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE2 */
 #define EUR_CR_BIF_TILE2                    0x0C14
 #define EUR_CR_BIF_TILE2_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE2_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE2_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE2_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE2_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE3 */
 #define EUR_CR_BIF_TILE3                    0x0C18
 #define EUR_CR_BIF_TILE3_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE3_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE3_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE3_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE3_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE4 */
 #define EUR_CR_BIF_TILE4                    0x0C1C
 #define EUR_CR_BIF_TILE4_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE4_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE4_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE4_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE4_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE5 */
 #define EUR_CR_BIF_TILE5                    0x0C20
 #define EUR_CR_BIF_TILE5_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE5_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE5_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE5_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE5_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE6 */
 #define EUR_CR_BIF_TILE6                    0x0C24
 #define EUR_CR_BIF_TILE6_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE6_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE6_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE6_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE6_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE7 */
 #define EUR_CR_BIF_TILE7                    0x0C28
 #define EUR_CR_BIF_TILE7_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE7_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE7_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE7_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE7_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE8 */
 #define EUR_CR_BIF_TILE8                    0x0C2C
 #define EUR_CR_BIF_TILE8_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE8_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE8_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE8_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE8_CFG_SIGNED         0
+/* Register EUR_CR_BIF_TILE9 */
 #define EUR_CR_BIF_TILE9                    0x0C30
 #define EUR_CR_BIF_TILE9_MIN_ADDRESS_MASK   0x00000FFFU
 #define EUR_CR_BIF_TILE9_MIN_ADDRESS_SHIFT  0
 #define EUR_CR_BIF_TILE9_CFG_MASK           0x0F000000U
 #define EUR_CR_BIF_TILE9_CFG_SHIFT          24
 #define EUR_CR_BIF_TILE9_CFG_SIGNED         0
+/* Register EUR_CR_BIF_CTRL_INVAL */
 #define EUR_CR_BIF_CTRL_INVAL               0x0C34
 #define EUR_CR_BIF_CTRL_INVAL_PTE_MASK      0x00000004U
 #define EUR_CR_BIF_CTRL_INVAL_PTE_SHIFT     2
 #define EUR_CR_BIF_CTRL_INVAL_ALL_MASK      0x00000008U
 #define EUR_CR_BIF_CTRL_INVAL_ALL_SHIFT     3
 #define EUR_CR_BIF_CTRL_INVAL_ALL_SIGNED    0
+/* Register EUR_CR_BIF_DIR_LIST_BASE1 */
 #define EUR_CR_BIF_DIR_LIST_BASE1           0x0C38
 #define EUR_CR_BIF_DIR_LIST_BASE1_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE1_ADDR_SHIFT 12
 #define EUR_CR_BIF_DIR_LIST_BASE1_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_DIR_LIST_BASE2 */
 #define EUR_CR_BIF_DIR_LIST_BASE2           0x0C3C
 #define EUR_CR_BIF_DIR_LIST_BASE2_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE2_ADDR_SHIFT 12
 #define EUR_CR_BIF_DIR_LIST_BASE2_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_DIR_LIST_BASE3 */
 #define EUR_CR_BIF_DIR_LIST_BASE3           0x0C40
 #define EUR_CR_BIF_DIR_LIST_BASE3_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE3_ADDR_SHIFT 12
 #define EUR_CR_BIF_DIR_LIST_BASE3_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_DIR_LIST_BASE4 */
 #define EUR_CR_BIF_DIR_LIST_BASE4           0x0C44
 #define EUR_CR_BIF_DIR_LIST_BASE4_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE4_ADDR_SHIFT 12
 #define EUR_CR_BIF_DIR_LIST_BASE4_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_DIR_LIST_BASE5 */
 #define EUR_CR_BIF_DIR_LIST_BASE5           0x0C48
 #define EUR_CR_BIF_DIR_LIST_BASE5_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE5_ADDR_SHIFT 12
 #define EUR_CR_BIF_DIR_LIST_BASE5_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_DIR_LIST_BASE6 */
 #define EUR_CR_BIF_DIR_LIST_BASE6           0x0C4C
 #define EUR_CR_BIF_DIR_LIST_BASE6_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE6_ADDR_SHIFT 12
 #define EUR_CR_BIF_DIR_LIST_BASE6_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_DIR_LIST_BASE7 */
 #define EUR_CR_BIF_DIR_LIST_BASE7           0x0C50
 #define EUR_CR_BIF_DIR_LIST_BASE7_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE7_ADDR_SHIFT 12
 #define EUR_CR_BIF_DIR_LIST_BASE7_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_BANK_SET */
 #define EUR_CR_BIF_BANK_SET                 0x0C74
 #define EUR_CR_BIF_BANK_SET_SELECT_2D_MASK  0x00000001U
 #define EUR_CR_BIF_BANK_SET_SELECT_2D_SHIFT 0
 #define EUR_CR_BIF_BANK_SET_SELECT_DPM_LSS_MASK 0x00000200U
 #define EUR_CR_BIF_BANK_SET_SELECT_DPM_LSS_SHIFT 9
 #define EUR_CR_BIF_BANK_SET_SELECT_DPM_LSS_SIGNED 0
+/* Register EUR_CR_BIF_BANK0 */
 #define EUR_CR_BIF_BANK0                    0x0C78
 #define EUR_CR_BIF_BANK0_INDEX_EDM_MASK     0x0000000FU
 #define EUR_CR_BIF_BANK0_INDEX_EDM_SHIFT    0
 #define EUR_CR_BIF_BANK0_INDEX_PTLA_MASK    0x000F0000U
 #define EUR_CR_BIF_BANK0_INDEX_PTLA_SHIFT   16
 #define EUR_CR_BIF_BANK0_INDEX_PTLA_SIGNED  0
+/* Register EUR_CR_BIF_BANK1 */
 #define EUR_CR_BIF_BANK1                    0x0C7C
 #define EUR_CR_BIF_BANK1_INDEX_EDM_MASK     0x0000000FU
 #define EUR_CR_BIF_BANK1_INDEX_EDM_SHIFT    0
 #define EUR_CR_BIF_BANK1_INDEX_3D_MASK      0x0000F000U
 #define EUR_CR_BIF_BANK1_INDEX_3D_SHIFT     12
 #define EUR_CR_BIF_BANK1_INDEX_3D_SIGNED    0
+/* Register EUR_CR_BIF_DIR_LIST_BASE0 */
 #define EUR_CR_BIF_DIR_LIST_BASE0           0x0C84
 #define EUR_CR_BIF_DIR_LIST_BASE0_ADDR_MASK 0xFFFFF000U
 #define EUR_CR_BIF_DIR_LIST_BASE0_ADDR_SHIFT 12
 #define EUR_CR_BIF_DIR_LIST_BASE0_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_TA_REQ_BASE */
 #define EUR_CR_BIF_TA_REQ_BASE              0x0C90
 #define EUR_CR_BIF_TA_REQ_BASE_ADDR_MASK    0xFFF00000U
 #define EUR_CR_BIF_TA_REQ_BASE_ADDR_SHIFT   20
 #define EUR_CR_BIF_TA_REQ_BASE_ADDR_SIGNED  0
+/* Register EUR_CR_BIF_MEM_REQ_STAT */
 #define EUR_CR_BIF_MEM_REQ_STAT             0x0CA8
 #define EUR_CR_BIF_MEM_REQ_STAT_READS_MASK  0x000000FFU
 #define EUR_CR_BIF_MEM_REQ_STAT_READS_SHIFT 0
 #define EUR_CR_BIF_MEM_REQ_STAT_READS_SIGNED 0
+/* Register EUR_CR_BIF_3D_REQ_BASE */
 #define EUR_CR_BIF_3D_REQ_BASE              0x0CAC
 #define EUR_CR_BIF_3D_REQ_BASE_ADDR_MASK    0xFFF00000U
 #define EUR_CR_BIF_3D_REQ_BASE_ADDR_SHIFT   20
 #define EUR_CR_BIF_3D_REQ_BASE_ADDR_SIGNED  0
+/* Register EUR_CR_BIF_ZLS_REQ_BASE */
 #define EUR_CR_BIF_ZLS_REQ_BASE             0x0CB0
 #define EUR_CR_BIF_ZLS_REQ_BASE_ADDR_MASK   0xFFF00000U
 #define EUR_CR_BIF_ZLS_REQ_BASE_ADDR_SHIFT  20
 #define EUR_CR_BIF_ZLS_REQ_BASE_ADDR_SIGNED 0
+/* Register EUR_CR_BIF_BANK_STATUS */
 #define EUR_CR_BIF_BANK_STATUS              0x0CB4
 #define EUR_CR_BIF_BANK_STATUS_3D_CURRENT_BANK_MASK 0x00000001U
 #define EUR_CR_BIF_BANK_STATUS_3D_CURRENT_BANK_SHIFT 0
 #define EUR_CR_BIF_BANK_STATUS_TA_CURRENT_BANK_MASK 0x00000002U
 #define EUR_CR_BIF_BANK_STATUS_TA_CURRENT_BANK_SHIFT 1
 #define EUR_CR_BIF_BANK_STATUS_TA_CURRENT_BANK_SIGNED 0
+/* Register EUR_CR_BIF_MMU_CTRL */
 #define EUR_CR_BIF_MMU_CTRL                 0x0CD0
 #define EUR_CR_BIF_MMU_CTRL_PREFETCHING_ON_MASK 0x00000001U
 #define EUR_CR_BIF_MMU_CTRL_PREFETCHING_ON_SHIFT 0
 #define EUR_CR_BIF_MMU_CTRL_DISABLE_BURST_EXP_MASK 0x00000020U
 #define EUR_CR_BIF_MMU_CTRL_DISABLE_BURST_EXP_SHIFT 5
 #define EUR_CR_BIF_MMU_CTRL_DISABLE_BURST_EXP_SIGNED 0
+/* Register EUR_CR_2D_BLIT_STATUS */
 #define EUR_CR_2D_BLIT_STATUS               0x0E04
 #define EUR_CR_2D_BLIT_STATUS_COMPLETE_MASK 0x00FFFFFFU
 #define EUR_CR_2D_BLIT_STATUS_COMPLETE_SHIFT 0
 #define EUR_CR_2D_BLIT_STATUS_BUSY_MASK     0x01000000U
 #define EUR_CR_2D_BLIT_STATUS_BUSY_SHIFT    24
 #define EUR_CR_2D_BLIT_STATUS_BUSY_SIGNED   0
+/* Register EUR_CR_2D_VIRTUAL_FIFO_0 */
 #define EUR_CR_2D_VIRTUAL_FIFO_0            0x0E10
 #define EUR_CR_2D_VIRTUAL_FIFO_0_ENABLE_MASK 0x00000001U
 #define EUR_CR_2D_VIRTUAL_FIFO_0_ENABLE_SHIFT 0
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_MUL_MASK 0x0000F000U
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_MUL_SHIFT 12
 #define EUR_CR_2D_VIRTUAL_FIFO_0_FLOWRATE_MUL_SIGNED 0
+/* Register EUR_CR_2D_VIRTUAL_FIFO_1 */
 #define EUR_CR_2D_VIRTUAL_FIFO_1            0x0E14
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_ACC_MASK 0x00000FFFU
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_ACC_SHIFT 0
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_METRIC_MASK 0xFF000000U
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_METRIC_SHIFT 24
 #define EUR_CR_2D_VIRTUAL_FIFO_1_MIN_METRIC_SIGNED 0
+/* Register EUR_CR_BREAKPOINT0_START */
 #define EUR_CR_BREAKPOINT0_START            0x0F44
 #define EUR_CR_BREAKPOINT0_START_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT0_START_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT0_START_ADDRESS_SIGNED 0
+/* Register EUR_CR_BREAKPOINT0_END */
 #define EUR_CR_BREAKPOINT0_END              0x0F48
 #define EUR_CR_BREAKPOINT0_END_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT0_END_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT0_END_ADDRESS_SIGNED 0
+/* Register EUR_CR_BREAKPOINT0 */
 #define EUR_CR_BREAKPOINT0                  0x0F4C
 #define EUR_CR_BREAKPOINT0_MASK_DM_MASK     0x00000038U
 #define EUR_CR_BREAKPOINT0_MASK_DM_SHIFT    3
 #define EUR_CR_BREAKPOINT0_CTRL_RENABLE_MASK 0x00000001U
 #define EUR_CR_BREAKPOINT0_CTRL_RENABLE_SHIFT 0
 #define EUR_CR_BREAKPOINT0_CTRL_RENABLE_SIGNED 0
+/* Register EUR_CR_BREAKPOINT1_START */
 #define EUR_CR_BREAKPOINT1_START            0x0F50
 #define EUR_CR_BREAKPOINT1_START_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT1_START_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT1_START_ADDRESS_SIGNED 0
+/* Register EUR_CR_BREAKPOINT1_END */
 #define EUR_CR_BREAKPOINT1_END              0x0F54
 #define EUR_CR_BREAKPOINT1_END_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT1_END_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT1_END_ADDRESS_SIGNED 0
+/* Register EUR_CR_BREAKPOINT1 */
 #define EUR_CR_BREAKPOINT1                  0x0F58
 #define EUR_CR_BREAKPOINT1_MASK_DM_MASK     0x00000038U
 #define EUR_CR_BREAKPOINT1_MASK_DM_SHIFT    3
 #define EUR_CR_BREAKPOINT1_CTRL_RENABLE_MASK 0x00000001U
 #define EUR_CR_BREAKPOINT1_CTRL_RENABLE_SHIFT 0
 #define EUR_CR_BREAKPOINT1_CTRL_RENABLE_SIGNED 0
+/* Register EUR_CR_BREAKPOINT2_START */
 #define EUR_CR_BREAKPOINT2_START            0x0F5C
 #define EUR_CR_BREAKPOINT2_START_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT2_START_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT2_START_ADDRESS_SIGNED 0
+/* Register EUR_CR_BREAKPOINT2_END */
 #define EUR_CR_BREAKPOINT2_END              0x0F60
 #define EUR_CR_BREAKPOINT2_END_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT2_END_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT2_END_ADDRESS_SIGNED 0
+/* Register EUR_CR_BREAKPOINT2 */
 #define EUR_CR_BREAKPOINT2                  0x0F64
 #define EUR_CR_BREAKPOINT2_MASK_DM_MASK     0x00000038U
 #define EUR_CR_BREAKPOINT2_MASK_DM_SHIFT    3
 #define EUR_CR_BREAKPOINT2_CTRL_RENABLE_MASK 0x00000001U
 #define EUR_CR_BREAKPOINT2_CTRL_RENABLE_SHIFT 0
 #define EUR_CR_BREAKPOINT2_CTRL_RENABLE_SIGNED 0
+/* Register EUR_CR_BREAKPOINT3_START */
 #define EUR_CR_BREAKPOINT3_START            0x0F68
 #define EUR_CR_BREAKPOINT3_START_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT3_START_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT3_START_ADDRESS_SIGNED 0
+/* Register EUR_CR_BREAKPOINT3_END */
 #define EUR_CR_BREAKPOINT3_END              0x0F6C
 #define EUR_CR_BREAKPOINT3_END_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT3_END_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT3_END_ADDRESS_SIGNED 0
+/* Register EUR_CR_BREAKPOINT3 */
 #define EUR_CR_BREAKPOINT3                  0x0F70
 #define EUR_CR_BREAKPOINT3_MASK_DM_MASK     0x00000038U
 #define EUR_CR_BREAKPOINT3_MASK_DM_SHIFT    3
 #define EUR_CR_BREAKPOINT3_CTRL_RENABLE_MASK 0x00000001U
 #define EUR_CR_BREAKPOINT3_CTRL_RENABLE_SHIFT 0
 #define EUR_CR_BREAKPOINT3_CTRL_RENABLE_SIGNED 0
+/* Register EUR_CR_BREAKPOINT_READ */
 #define EUR_CR_BREAKPOINT_READ              0x0F74
 #define EUR_CR_BREAKPOINT_READ_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_BREAKPOINT_READ_ADDRESS_SHIFT 4
 #define EUR_CR_BREAKPOINT_READ_ADDRESS_SIGNED 0
+/* Register EUR_CR_PARTITION_BREAKPOINT_TRAP */
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP    0x0F78
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_CONTINUE_MASK 0x00000002U
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_CONTINUE_SHIFT 1
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_WRNOTIFY_MASK 0x00000001U
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_WRNOTIFY_SHIFT 0
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_WRNOTIFY_SIGNED 0
+/* Register EUR_CR_PARTITION_BREAKPOINT */
 #define EUR_CR_PARTITION_BREAKPOINT         0x0F7C
 #define EUR_CR_PARTITION_BREAKPOINT_MODULE_ID_MASK 0x000003C0U
 #define EUR_CR_PARTITION_BREAKPOINT_MODULE_ID_SHIFT 6
 #define EUR_CR_PARTITION_BREAKPOINT_TRAPPED_MASK 0x00000004U
 #define EUR_CR_PARTITION_BREAKPOINT_TRAPPED_SHIFT 2
 #define EUR_CR_PARTITION_BREAKPOINT_TRAPPED_SIGNED 0
+/* Register EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO0 */
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO0 0x0F80
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO0_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO0_ADDRESS_SHIFT 4
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO0_ADDRESS_SIGNED 0
+/* Register EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1 */
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1 0x0F84
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_SIZE_MASK 0x00007C00U
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_SIZE_SHIFT 10
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_RNW_MASK 0x00000001U
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_RNW_SHIFT 0
 #define EUR_CR_PARTITION_BREAKPOINT_TRAP_INFO1_RNW_SIGNED 0
+/* Register EUR_CR_USE_CODE_BASE_0 */
 #define EUR_CR_USE_CODE_BASE_0              0x0A0C
 #define EUR_CR_USE_CODE_BASE_ADDR_00_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_00_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_00_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_00_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_00_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_1 */
 #define EUR_CR_USE_CODE_BASE_1              0x0A10
 #define EUR_CR_USE_CODE_BASE_ADDR_01_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_01_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_01_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_01_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_01_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_2 */
 #define EUR_CR_USE_CODE_BASE_2              0x0A14
 #define EUR_CR_USE_CODE_BASE_ADDR_02_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_02_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_02_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_02_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_02_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_3 */
 #define EUR_CR_USE_CODE_BASE_3              0x0A18
 #define EUR_CR_USE_CODE_BASE_ADDR_03_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_03_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_03_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_03_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_03_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_4 */
 #define EUR_CR_USE_CODE_BASE_4              0x0A1C
 #define EUR_CR_USE_CODE_BASE_ADDR_04_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_04_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_04_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_04_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_04_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_5 */
 #define EUR_CR_USE_CODE_BASE_5              0x0A20
 #define EUR_CR_USE_CODE_BASE_ADDR_05_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_05_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_05_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_05_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_05_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_6 */
 #define EUR_CR_USE_CODE_BASE_6              0x0A24
 #define EUR_CR_USE_CODE_BASE_ADDR_06_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_06_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_06_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_06_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_06_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_7 */
 #define EUR_CR_USE_CODE_BASE_7              0x0A28
 #define EUR_CR_USE_CODE_BASE_ADDR_07_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_07_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_07_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_07_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_07_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_8 */
 #define EUR_CR_USE_CODE_BASE_8              0x0A2C
 #define EUR_CR_USE_CODE_BASE_ADDR_08_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_08_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_08_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_08_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_08_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_9 */
 #define EUR_CR_USE_CODE_BASE_9              0x0A30
 #define EUR_CR_USE_CODE_BASE_ADDR_09_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_09_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_09_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_09_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_09_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_10 */
 #define EUR_CR_USE_CODE_BASE_10             0x0A34
 #define EUR_CR_USE_CODE_BASE_ADDR_10_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_10_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_10_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_10_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_10_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_11 */
 #define EUR_CR_USE_CODE_BASE_11             0x0A38
 #define EUR_CR_USE_CODE_BASE_ADDR_11_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_11_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_11_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_11_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_11_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_12 */
 #define EUR_CR_USE_CODE_BASE_12             0x0A3C
 #define EUR_CR_USE_CODE_BASE_ADDR_12_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_12_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_12_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_12_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_12_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_13 */
 #define EUR_CR_USE_CODE_BASE_13             0x0A40
 #define EUR_CR_USE_CODE_BASE_ADDR_13_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_13_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_13_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_13_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_13_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_14 */
 #define EUR_CR_USE_CODE_BASE_14             0x0A44
 #define EUR_CR_USE_CODE_BASE_ADDR_14_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_14_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_14_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_14_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_14_SIGNED   0
+/* Register EUR_CR_USE_CODE_BASE_15 */
 #define EUR_CR_USE_CODE_BASE_15             0x0A48
 #define EUR_CR_USE_CODE_BASE_ADDR_15_MASK   0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_15_SHIFT  0
 #define EUR_CR_USE_CODE_BASE_DM_15_MASK     0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_15_SHIFT    26
 #define EUR_CR_USE_CODE_BASE_DM_15_SIGNED   0
+/* Register EUR_CR_PIPE0_BREAKPOINT_TRAP */
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP        0x0F88
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_CONTINUE_MASK 0x00000002U
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_CONTINUE_SHIFT 1
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_WRNOTIFY_MASK 0x00000001U
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_WRNOTIFY_SHIFT 0
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_WRNOTIFY_SIGNED 0
+/* Register EUR_CR_PIPE0_BREAKPOINT */
 #define EUR_CR_PIPE0_BREAKPOINT             0x0F8C
 #define EUR_CR_PIPE0_BREAKPOINT_MODULE_ID_MASK 0x000003C0U
 #define EUR_CR_PIPE0_BREAKPOINT_MODULE_ID_SHIFT 6
 #define EUR_CR_PIPE0_BREAKPOINT_TRAPPED_MASK 0x00000004U
 #define EUR_CR_PIPE0_BREAKPOINT_TRAPPED_SHIFT 2
 #define EUR_CR_PIPE0_BREAKPOINT_TRAPPED_SIGNED 0
+/* Register EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO0 */
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO0  0x0F90
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO0_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO0_ADDRESS_SHIFT 4
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO0_ADDRESS_SIGNED 0
+/* Register EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO1 */
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO1  0x0F94
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO1_SIZE_MASK 0x00007C00U
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO1_SIZE_SHIFT 10
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO1_RNW_MASK 0x00000001U
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO1_RNW_SHIFT 0
 #define EUR_CR_PIPE0_BREAKPOINT_TRAP_INFO1_RNW_SIGNED 0
+/* Register EUR_CR_PIPE1_BREAKPOINT_TRAP */
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP        0x0F98
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_CONTINUE_MASK 0x00000002U
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_CONTINUE_SHIFT 1
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_WRNOTIFY_MASK 0x00000001U
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_WRNOTIFY_SHIFT 0
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_WRNOTIFY_SIGNED 0
+/* Register EUR_CR_PIPE1_BREAKPOINT */
 #define EUR_CR_PIPE1_BREAKPOINT             0x0F9C
 #define EUR_CR_PIPE1_BREAKPOINT_MODULE_ID_MASK 0x000003C0U
 #define EUR_CR_PIPE1_BREAKPOINT_MODULE_ID_SHIFT 6
 #define EUR_CR_PIPE1_BREAKPOINT_TRAPPED_MASK 0x00000004U
 #define EUR_CR_PIPE1_BREAKPOINT_TRAPPED_SHIFT 2
 #define EUR_CR_PIPE1_BREAKPOINT_TRAPPED_SIGNED 0
+/* Register EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO0 */
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO0  0x0FA0
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO0_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO0_ADDRESS_SHIFT 4
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO0_ADDRESS_SIGNED 0
+/* Register EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO1 */
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO1  0x0FA4
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO1_SIZE_MASK 0x00007C00U
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO1_SIZE_SHIFT 10
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO1_RNW_MASK 0x00000001U
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO1_RNW_SHIFT 0
 #define EUR_CR_PIPE1_BREAKPOINT_TRAP_INFO1_RNW_SIGNED 0
+/* Table EUR_CR_USE_CODE_BASE */
+/* Register EUR_CR_USE_CODE_BASE */
 #define EUR_CR_USE_CODE_BASE(X)     (0x0A0C + (4 * (X)))
 #define EUR_CR_USE_CODE_BASE_ADDR_MASK      0x03FFFFFFU
 #define EUR_CR_USE_CODE_BASE_ADDR_SHIFT     0
 #define EUR_CR_USE_CODE_BASE_DM_MASK        0x0C000000U
 #define EUR_CR_USE_CODE_BASE_DM_SHIFT       26
 #define EUR_CR_USE_CODE_BASE_DM_SIGNED      0
+/* Number of entries in table EUR_CR_USE_CODE_BASE */
 #define EUR_CR_USE_CODE_BASE_SIZE_UINT32 16
 #define EUR_CR_USE_CODE_BASE_NUM_ENTRIES 16
 
-#endif 
+#endif /* _SGX544DEFS_KM_H_ */
 
index b3a2583..ed24647 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX hw definitions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _SGXDEFS_H_
 #define        _SGXDEFS_H_
 #include "sgxmpplusdefs.h"
 #else
 #include "sgxmpdefs.h"
-#endif 
-#else 
+#endif /* SGX554 */
+#else /* SGX_FEATURE_MP */
 #if defined(SGX_FEATURE_SYSTEM_CACHE)
 #include "mnemedefs.h"
 #endif
-#endif 
+#endif /* SGX_FEATURE_MP */
+
+/*****************************************************************************
+ Core specific defines.
+*****************************************************************************/
 
-#endif 
+#endif /* _SGXDEFS_H_ */
 
+/*****************************************************************************
+ End of file (sgxdefs.h)
+*****************************************************************************/
index c539bc4..711e356 100644 (file)
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX HW errata definitions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Specifies associations between SGX core revisions
+                and SW workarounds required to fix HW errata that exist
+                in specific core revisions
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef _SGXERRATA_KM_H_
 #define _SGXERRATA_KM_H_
 
+/* ignore warnings about unrecognised preprocessing directives in conditional inclusion directives */
+/* PRQA S 3115 ++ */
+
 #if defined(SGX520) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX520 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
-       #if SGX_CORE_REV == 100
-               #define FIX_HW_BRN_28889
-       #else
        #if SGX_CORE_REV == 111
        #else
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
-               
+               /* RTL head - no BRNs to apply */
        #else
                #error "sgxerrata.h: SGX520 Core Revision unspecified"
        #endif
        #endif
-       #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
 #if defined(SGX530) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX530 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
-       #if SGX_CORE_REV == 110
-               #define FIX_HW_BRN_22934
-               #define FIX_HW_BRN_28889
-       #else
-       #if SGX_CORE_REV == 111
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_28889
-       #else
-       #if SGX_CORE_REV == 1111
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_28889
-       #else
        #if SGX_CORE_REV == 120
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_28889
+               #define FIX_HW_BRN_22934/* Workaround in sgx featuredefs */     
+               #define FIX_HW_BRN_28889/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == 121
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_28889
+               #define FIX_HW_BRN_22934/* Workaround in sgx featuredefs */     
+               #define FIX_HW_BRN_28889/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == 125
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_28889
+               #define FIX_HW_BRN_22934/* Workaround in sgx featuredefs */     
+               #define FIX_HW_BRN_28889/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == 130
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_28889
+               #define FIX_HW_BRN_22934/* Workaround in sgx featuredefs */     
+               #define FIX_HW_BRN_28889/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
-               
+               /* RTL head - no BRNs to apply */
        #else
                #error "sgxerrata.h: SGX530 Core Revision unspecified"
        #endif
        #endif
        #endif
-       #endif
-       #endif
-       #endif
 #endif
         #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
 #if defined(SGX531) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX531 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
        #if SGX_CORE_REV == 101
-               #define FIX_HW_BRN_26620
-               #define FIX_HW_BRN_28011
-               #define FIX_HW_BRN_34028
+               #define FIX_HW_BRN_26620/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_28011/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_34028/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == 110
-               #define FIX_HW_BRN_34028
+               #define FIX_HW_BRN_34028/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
-               
+               /* RTL head - no BRNs to apply */
        #else
                #error "sgxerrata.h: SGX531 Core Revision unspecified"
        #endif
        #endif
        #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
 #if (defined(SGX535) || defined(SGX535_V1_1)) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX535 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
-       #if SGX_CORE_REV == 112
-               #define FIX_HW_BRN_23281
-               #define FIX_HW_BRN_23410 
-               #define FIX_HW_BRN_22693
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_22997
-               #define FIX_HW_BRN_23030
-       #else
-       #if SGX_CORE_REV == 113
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_23281
-               #define FIX_HW_BRN_23944
-               #define FIX_HW_BRN_23410
-       #else
        #if SGX_CORE_REV == 121
-               #define FIX_HW_BRN_22934        
-               #define FIX_HW_BRN_23944
-               #define FIX_HW_BRN_23410
+               #define FIX_HW_BRN_22934/* Workaround in sgx featuredefs */     
+               #define FIX_HW_BRN_23944/* Workaround in code (services) */
+               #define FIX_HW_BRN_23410/* Workaround in code (services) and ucode */
        #else
        #if SGX_CORE_REV == 126
-               #define FIX_HW_BRN_22934        
+               #define FIX_HW_BRN_22934/* Workaround in sgx featuredefs */     
        #else   
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
-               
+               /* RTL head - no BRNs to apply */
        #else
                #error "sgxerrata.h: SGX535 Core Revision unspecified"
 
        #endif
        #endif
        #endif
-       #endif
-       #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
 #if defined(SGX540) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX540 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
        #if SGX_CORE_REV == 101
-               #define FIX_HW_BRN_25499
-               #define FIX_HW_BRN_25503
-               #define FIX_HW_BRN_26620
-               #define FIX_HW_BRN_28011
-               #define FIX_HW_BRN_34028
+               #define FIX_HW_BRN_25499/* Workaround in sgx featuredefs */
+               #define FIX_HW_BRN_25503/* Workaround in code (services) */
+               #define FIX_HW_BRN_26620/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_28011/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_34028/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == 110
-               #define FIX_HW_BRN_25503
-               #define FIX_HW_BRN_26620
-               #define FIX_HW_BRN_28011
-               #define FIX_HW_BRN_34028
+               #define FIX_HW_BRN_25503/* Workaround in code (services) */
+               #define FIX_HW_BRN_26620/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_28011/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_34028/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == 120
-               #define FIX_HW_BRN_26620
-               #define FIX_HW_BRN_28011
-               #define FIX_HW_BRN_34028
+               #define FIX_HW_BRN_26620/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_28011/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_34028/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == 121
-               #define FIX_HW_BRN_28011
-               #define FIX_HW_BRN_34028
+               #define FIX_HW_BRN_28011/* Workaround in services (srvkm) */
+               #define FIX_HW_BRN_34028/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == 130
-               #define FIX_HW_BRN_34028
+               #define FIX_HW_BRN_34028/* Workaround in services (srvkm) */
        #else
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
-               
+               /* RTL head - no BRNs to apply */
        #else
                #error "sgxerrata.h: SGX540 Core Revision unspecified"
        #endif
        #endif
        #endif
        #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
-#if defined(SGX541) && !defined(SGX_CORE_DEFINED)
-       #if defined(SGX_FEATURE_MP)
-               
-               #define SGX_CORE_REV_HEAD       0
-               #if defined(USE_SGX_CORE_REV_HEAD)
-                       
-                       #define SGX_CORE_REV    SGX_CORE_REV_HEAD
-               #endif
-
-               #if SGX_CORE_REV == 100
-                       #define FIX_HW_BRN_27270
-                       #define FIX_HW_BRN_28011
-                       #define FIX_HW_BRN_27510
-                       
-               #else
-               #if SGX_CORE_REV == SGX_CORE_REV_HEAD
-                       
-               #else
-                       #error "sgxerrata.h: SGX541 Core Revision unspecified"
-               #endif
-               #endif
-               
-               #define SGX_CORE_DEFINED
-       #else 
-               #error "sgxerrata.h: SGX541 only supports MP configs (SGX_FEATURE_MP)"
-       #endif 
-#endif
 
 #if defined(SGX543) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX543 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
-       #if SGX_CORE_REV == 113
-               #define FIX_HW_BRN_29954
-               #define FIX_HW_BRN_29997
-               #define FIX_HW_BRN_30954
-               #define FIX_HW_BRN_31093
-               #define FIX_HW_BRN_31195
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31278
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-               #define FIX_HW_BRN_31620
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_31542
-               #define FIX_HW_BRN_32044 
-               #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
-               #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
-       #else
        #if SGX_CORE_REV == 122
-               #define FIX_HW_BRN_29954
-               #define FIX_HW_BRN_29997
-               #define FIX_HW_BRN_30954
-               #define FIX_HW_BRN_31093
-               #define FIX_HW_BRN_31195
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31278
+               #define FIX_HW_BRN_29954/* turns off regbank split feature */
+               #define FIX_HW_BRN_29997/* workaround in services */
+               #define FIX_HW_BRN_30954/* workaround in services */
+               #define FIX_HW_BRN_31093/* workaround in services */
+               #define FIX_HW_BRN_31195/* workaround in services */
+               #define FIX_HW_BRN_31272/* workaround in services (srvclient) and uKernel */
+               #define FIX_HW_BRN_31278/* disabled prefetching in MMU */
+               #define FIX_HW_BRN_31542/* workaround in uKernel and Services */
                #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+                       #define FIX_HW_BRN_31559/* workaround in services and uKernel */
                #endif
-               #define FIX_HW_BRN_31620
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_31542
-               #define FIX_HW_BRN_32044 
-               #define FIX_HW_BRN_32085 
+               #define FIX_HW_BRN_31620/* workaround in services */
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
+               #define FIX_HW_BRN_32044 /* workaround in uKernel, services and client drivers */
+               #define FIX_HW_BRN_32085 /* workaround in services: prefetch fix applied, investigating PT based fix */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
-                       
+               #define FIX_HW_BRN_33920/* workaround in ukernel */
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
+                       /* add BRNs here */
        #else
        #if SGX_CORE_REV == 1221
-               #define FIX_HW_BRN_29954
-        #define FIX_HW_BRN_31195
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31278
+               #define FIX_HW_BRN_29954/* turns off regbank split feature */
+        #define FIX_HW_BRN_31195/* workaround in services */
+               #define FIX_HW_BRN_31272/* workaround in services (srvclient) and uKernel */
+               #define FIX_HW_BRN_31278/* disabled prefetching in MMU */
                #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+                       #define FIX_HW_BRN_31559/* workaround in services and uKernel */
                #endif
-               #define FIX_HW_BRN_31542
-               #define FIX_HW_BRN_31671                
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_32044
-               #define FIX_HW_BRN_32085 
+               #define FIX_HW_BRN_31542/* workaround in uKernel and Services */
+               #define FIX_HW_BRN_31671/* workaround in uKernel */             
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
+               #define FIX_HW_BRN_32044/* workaround in uKernel, services and client drivers */
+               #define FIX_HW_BRN_32085 /* workaround in services: prefetch fix applied, investigating PT based fix */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
-               #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
-                       
-       #else
-       #if SGX_CORE_REV == 140
-               #define FIX_HW_BRN_29954
-               #define FIX_HW_BRN_30954
-               #define FIX_HW_BRN_31093
-               #define FIX_HW_BRN_31195
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31278
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_31620
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_31542
-               #define FIX_HW_BRN_32044 
-               #define FIX_HW_BRN_32085 
-               #define FIX_HW_BRN_33920
-               #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
-               #endif
-               #define FIX_HW_BRN_36513 
-                       
-       #else
-       #if SGX_CORE_REV == 1401
-               #define FIX_HW_BRN_29954
-               #define FIX_HW_BRN_30954
-               #define FIX_HW_BRN_31195
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31278
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-               #define FIX_HW_BRN_31620
-               #define FIX_HW_BRN_31542
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_32044 
-               #define FIX_HW_BRN_32085 
-               #define FIX_HW_BRN_33920
-               #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
-               #endif
-               #define FIX_HW_BRN_36513 
-                       
+               #define FIX_HW_BRN_33920/* workaround in ukernel */
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
+                       /* add BRNs here */
        #else
        #if SGX_CORE_REV == 141
-               #define FIX_HW_BRN_29954
+               #define FIX_HW_BRN_29954/* turns off regbank split feature */
                #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+                       #define FIX_HW_BRN_31559/* workaround in services and uKernel */
                #endif
-               #define FIX_HW_BRN_31671 
-               #define FIX_HW_BRN_31780
+               #define FIX_HW_BRN_31671 /* workaround in uKernel */
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_36513 
-                       
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
+                       /* add BRNs here */
        #else
        #if SGX_CORE_REV == 142
-               #define FIX_HW_BRN_29954
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-               #define FIX_HW_BRN_31671 
-               #define FIX_HW_BRN_31780
-               #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
-               #endif
-               #define FIX_HW_BRN_36513 
-                       
-       #else
-       #if SGX_CORE_REV == 211
-               #define FIX_HW_BRN_31093
-               #define FIX_HW_BRN_31195
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31278
+               #define FIX_HW_BRN_29954/* turns off regbank split feature */
                #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+                       #define FIX_HW_BRN_31559/* workaround in services and uKernel */
                #endif
-               #define FIX_HW_BRN_31620
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_31542
-               #define FIX_HW_BRN_32044 
-               #define FIX_HW_BRN_32085 
+               #define FIX_HW_BRN_31671 /* workaround in uKernel */
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
-                       
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
+                       /* add BRNs here */
        #else
        #if SGX_CORE_REV == 2111
-               #define FIX_HW_BRN_30982 
-               #define FIX_HW_BRN_31093
-               #define FIX_HW_BRN_31195
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31278
+               #define FIX_HW_BRN_30982 /* workaround in uKernel and services */
+               #define FIX_HW_BRN_31093/* workaround in services */
+               #define FIX_HW_BRN_31195/* workaround in services */
+               #define FIX_HW_BRN_31272/* workaround in services (srvclient) and uKernel */
+               #define FIX_HW_BRN_31278/* disabled prefetching in MMU */
+               #define FIX_HW_BRN_31542/* workaround in uKernel and Services */
                #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+                       #define FIX_HW_BRN_31559/* workaround in services and uKernel */
                #endif
-               #define FIX_HW_BRN_31620
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_31542
-               #define FIX_HW_BRN_32044 
-               #define FIX_HW_BRN_32085 
+               #define FIX_HW_BRN_31620/* workaround in services */
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
+               #define FIX_HW_BRN_32044 /* workaround in uKernel, services and client drivers */
+               #define FIX_HW_BRN_32085 /* workaround in services: prefetch fix applied, investigating PT based fix */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
-                       
+               #define FIX_HW_BRN_33920/* workaround in ukernel */
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
+                       /* add BRNs here */
        #else
        #if SGX_CORE_REV == 213
-               #define FIX_HW_BRN_31272
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+               #define FIX_HW_BRN_31272/* workaround in services (srvclient) and uKernel */
+               #if defined(SGX_FEATURE_MP)
+                       #define FIX_HW_BRN_31559/* workaround in services and uKernel */
                #endif
-               #define FIX_HW_BRN_31671 
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_32085 
+               #define FIX_HW_BRN_31671 /* workaround in uKernel */
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
+               #define FIX_HW_BRN_32085 /* workaround in services: prefetch fix applied, investigating PT based fix */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
-                       
+               #define FIX_HW_BRN_33920/* workaround in ukernel */
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
+                       /* add BRNs here */
        #else
        #if SGX_CORE_REV == 216
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_36513 
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
        #else
        #if SGX_CORE_REV == 302
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
+       #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
        #else
        #if SGX_CORE_REV == 303
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
+       #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
        #else
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
        #else
                #error "sgxerrata.h: SGX543 Core Revision unspecified"
        #endif
        #endif
        #endif
-       #endif
-       #endif
-       #endif
-       #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
 #if defined(SGX544) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX544 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
-       #if SGX_CORE_REV == 100
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-       #else
-       #if SGX_CORE_REV == 102
-               #define FIX_HW_BRN_29954
-               #define FIX_HW_BRN_31272
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_32085 
-               #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
-               #endif
-               #define FIX_HW_BRN_33920
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_36513 
-               #endif
-       #else
-       #if SGX_CORE_REV == 103
-               #define FIX_HW_BRN_29954
-               #define FIX_HW_BRN_31272
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_32085 
-               #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
-               #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
-       #else
        #if SGX_CORE_REV == 104
-               #define FIX_HW_BRN_29954
-               #define FIX_HW_BRN_31093
-               #define FIX_HW_BRN_31195
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31278
+               #define FIX_HW_BRN_29954/* turns off regbank split feature */
+               #define FIX_HW_BRN_31093/* workaround in services */
+               #define FIX_HW_BRN_31195/* workaround in services */
+               #define FIX_HW_BRN_31272/* workaround in services (srvclient) and uKernel */
+               #define FIX_HW_BRN_31278/* disabled prefetching in MMU */
                #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+                       #define FIX_HW_BRN_31559/* workaround in services and uKernel */
                #endif
-               #define FIX_HW_BRN_31542 
-               #define FIX_HW_BRN_31620
-               #define FIX_HW_BRN_31671 
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_32044 
-               #define FIX_HW_BRN_32085 
+               #define FIX_HW_BRN_31542 /* workaround in uKernel and Services */
+               #define FIX_HW_BRN_31620/* workaround in services */
+               #define FIX_HW_BRN_31671 /* workaround in uKernel */
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
+               #define FIX_HW_BRN_32044 /* workaround in uKernel, services and client drivers */
+               #define FIX_HW_BRN_32085 /* workaround in services: prefetch fix applied, investigating PT based fix */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
+               #define FIX_HW_BRN_33920/* workaround in ukernel */
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
        #else   
        #if SGX_CORE_REV == 105
                #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
+                       #define FIX_HW_BRN_31559/* workaround in services and uKernel */
                #endif
-               #define FIX_HW_BRN_31780
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_33920
-               #define FIX_HW_BRN_36513 
-       #else
-       #if SGX_CORE_REV == 106
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_31780
-               #define FIX_HW_BRN_33920
-       #else
-       #if SGX_CORE_REV == 110
-               #define FIX_HW_BRN_31272
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-               #define FIX_HW_BRN_31780
-               #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
-               #endif
-               #define FIX_HW_BRN_33920
+               #define FIX_HW_BRN_33920/* workaround in ukernel */
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
        #else
        #if SGX_CORE_REV == 112
-               #define FIX_HW_BRN_31272
-               #define FIX_HW_BRN_33920
+               #define FIX_HW_BRN_31272/* workaround in services (srvclient) and uKernel */
+               #define FIX_HW_BRN_33920/* workaround in ukernel */
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
        #else
        #if SGX_CORE_REV == 114
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-               #define FIX_HW_BRN_31780
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
+       #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
        #else
        #if SGX_CORE_REV == 115
-               #if defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_31425
-               #endif
-               #define FIX_HW_BRN_31780
+               #define FIX_HW_BRN_31780/* workaround in uKernel */
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #if defined(SGX_FEATURE_MP)
-                       #if SGX_FEATURE_MP_CORE_COUNT > 1
-                               #define FIX_HW_BRN_36513 
-                       #endif
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
+       #else
+       #if SGX_CORE_REV == 116
+               #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
+                       #define FIX_HW_BRN_33657/* workaround in ukernel */
                #endif
+               #define FIX_HW_BRN_33809/* workaround in kernel (enable burst combiner) */
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
        #else
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
        #else
                #error "sgxerrata.h: SGX544 Core Revision unspecified"
        #endif
        #endif
        #endif
-       #endif
-       #endif
-       #endif
-       #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
 #if defined(SGX545) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX545 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
-       #if SGX_CORE_REV == 100
-               #define FIX_HW_BRN_26620
-               #define FIX_HW_BRN_27266
-               #define FIX_HW_BRN_27456
-               #define FIX_HW_BRN_29702
-               #define FIX_HW_BRN_29823
-       #else
        #if SGX_CORE_REV == 109
-               #define FIX_HW_BRN_29702
-               #define FIX_HW_BRN_29823
-               #define FIX_HW_BRN_31939
-       #else
-       #if SGX_CORE_REV == 1012
-               #define FIX_HW_BRN_31939
-       #else
-       #if SGX_CORE_REV == 1013
-               #define FIX_HW_BRN_31939
+               #define FIX_HW_BRN_29702/* Workaround in services */
+               #define FIX_HW_BRN_29823/* Workaround in services */
+               #define FIX_HW_BRN_31939/* workaround in uKernel */
        #else
        #if SGX_CORE_REV == 10131
        #else
        #if SGX_CORE_REV == 10141
        #else
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
-               
+               /* RTL head - no BRNs to apply */
        #else
                #error "sgxerrata.h: SGX545 Core Revision unspecified"
        #endif
        #endif
        #endif
        #endif
-       #endif
-       #endif
-       #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
 #if defined(SGX554) && !defined(SGX_CORE_DEFINED)
-       
+       /* define the _current_ SGX554 RTL head revision */
        #define SGX_CORE_REV_HEAD       0
        #if defined(USE_SGX_CORE_REV_HEAD)
-               
+               /* build config selects Core Revision to be the Head */
                #define SGX_CORE_REV    SGX_CORE_REV_HEAD
        #endif
 
        #if SGX_CORE_REV == 1251
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
-               #define FIX_HW_BRN_36513 
-               
+               #define FIX_HW_BRN_36513 /* workaround in uKernel and Services */
+               /* add BRNs here */
        #else   
        #if SGX_CORE_REV == SGX_CORE_REV_HEAD
                #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && defined(SGX_FEATURE_MP)
-                       #define FIX_HW_BRN_33657
+                       #define FIX_HW_BRN_33657/* workaround in ukernel*/
                #endif
        #else
                #error "sgxerrata.h: SGX554 Core Revision unspecified"
        #endif
        #endif
-       
+       /* signal that the Core Version has a valid definition */
        #define SGX_CORE_DEFINED
 #endif
 
 #endif
 #endif
 
-#endif 
+/* restore warning */
+/* PRQA S 3115 -- */
+
+#endif /* _SGXERRATA_KM_H_ */
 
+/******************************************************************************
+ End of file (sgxerrata.h)
+******************************************************************************/
index 6427e7e..3e3a116 100644 (file)
@@ -1,29 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX fexture definitions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #if defined(SGX520)
        #define SGX_CORE_FRIENDLY_NAME                                                  "SGX520"
        #define SGX_CORE_ID                                                                             SGX_CORE_ID_520
        #define SGX_FEATURE_AUTOCLOCKGATING
        #define SGX_FEATURE_MONOLITHIC_UKERNEL
        #define SGX_FEATURE_MULTI_EVENT_KICK
+//     #define SGX_FEATURE_DATA_BREAKPOINTS
+//    #define SGX_FEATURE_PERPIPE_BKPT_REGS
+//    #define SGX_FEATURE_PERPIPE_BKPT_REGS_NUMPIPES          (2)
+//     #define SGX_FEATURE_2D_HARDWARE
+//     #define SGX_FEATURE_PTLA
        #define SGX_FEATURE_EXTENDED_PERF_COUNTERS
        #define SGX_FEATURE_EDM_VERTEX_PDSADDR_FULL_RANGE
        #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING)
                #if defined(SGX_FEATURE_MP)
                #define SGX_FEATURE_MASTER_VDM_CONTEXT_SWITCH
-               #endif
                #define SGX_FEATURE_SLAVE_VDM_CONTEXT_SWITCH
+               #endif
                #define SGX_FEATURE_SW_ISP_CONTEXT_SWITCH
        #endif
 #else
        #define SGX_FEATURE_MAX_TA_RENDER_TARGETS                               (512)
        #define SGX_FEATURE_SECONDARY_REQUIRES_USE_KICK
        #define SGX_FEATURE_WRITEBACK_DCU
-       
-       
+       //FIXME: this is defined in the build config for now
+       //#define SGX_FEATURE_36BIT_MMU
        #define SGX_FEATURE_BIF_WIDE_TILING_AND_4K_ADDRESS
        #define SGX_FEATURE_MULTI_EVENT_KICK
        #define SGX_FEATURE_EDM_VERTEX_PDSADDR_FULL_RANGE
        #define SGX_FEATURE_AUTOCLOCKGATING
        #define SGX_FEATURE_MONOLITHIC_UKERNEL
        #define SGX_FEATURE_MULTI_EVENT_KICK
+//     #define SGX_FEATURE_DATA_BREAKPOINTS
+//    #define SGX_FEATURE_PERPIPE_BKPT_REGS
+//    #define SGX_FEATURE_PERPIPE_BKPT_REGS_NUMPIPES          (2)
        #define SGX_FEATURE_2D_HARDWARE
        #define SGX_FEATURE_PTLA
        #define SGX_FEATURE_EXTENDED_PERF_COUNTERS
 
 #if defined(SGX_FEATURE_SLAVE_VDM_CONTEXT_SWITCH) \
        || defined(SGX_FEATURE_MASTER_VDM_CONTEXT_SWITCH)
+/* Enable the define so common code for HW VDMCS code is compiled */
 #define SGX_FEATURE_VDM_CONTEXT_SWITCH
 #endif
 
-#if defined(FIX_HW_BRN_22693)
-#undef SGX_FEATURE_AUTOCLOCKGATING
-#endif
+/*
+       'switch-off' features if defined BRNs affect the feature
+*/
 
 #if defined(FIX_HW_BRN_27266)
 #undef SGX_FEATURE_36BIT_MMU
 #endif
 
-#if defined(FIX_HW_BRN_27456)
-#undef SGX_FEATURE_BIF_WIDE_TILING_AND_4K_ADDRESS
-#endif
-
 #if defined(FIX_HW_BRN_22934)  \
        || defined(FIX_HW_BRN_25499)
 #undef SGX_FEATURE_MULTI_EVENT_KICK
 #undef SGX_FEATURE_BIF_NUM_DIRLISTS
 #endif
 
+/*
+       Derive other definitions:
+*/
+
+/* define default MP core count */
 #if defined(SGX_FEATURE_MP)
 #if defined(SGX_FEATURE_MP_CORE_COUNT_TA) && defined(SGX_FEATURE_MP_CORE_COUNT_3D)
 #if (SGX_FEATURE_MP_CORE_COUNT_TA > SGX_FEATURE_MP_CORE_COUNT_3D)
 #error Number of TA cores larger than number of 3D cores not supported in current driver
-#endif 
+#endif /* (SGX_FEATURE_MP_CORE_COUNT_TA > SGX_FEATURE_MP_CORE_COUNT_3D) */
 #else
 #if defined(SGX_FEATURE_MP_CORE_COUNT)
 #define SGX_FEATURE_MP_CORE_COUNT_TA           (SGX_FEATURE_MP_CORE_COUNT)
 #error Either SGX_FEATURE_MP_CORE_COUNT or \
 both SGX_FEATURE_MP_CORE_COUNT_TA and SGX_FEATURE_MP_CORE_COUNT_3D \
 must be defined when SGX_FEATURE_MP is defined
-#endif 
-#endif 
+#endif /* SGX_FEATURE_MP_CORE_COUNT */
+#endif /* defined(SGX_FEATURE_MP_CORE_COUNT_TA) && defined(SGX_FEATURE_MP_CORE_COUNT_3D) */
 #else
 #define SGX_FEATURE_MP_CORE_COUNT              (1)
 #define SGX_FEATURE_MP_CORE_COUNT_TA   (1)
 #define SGX_FEATURE_MP_CORE_COUNT_3D   (1)
-#endif 
+#endif /* SGX_FEATURE_MP */
 
 #if defined(SUPPORT_SGX_LOW_LATENCY_SCHEDULING) && !defined(SUPPORT_SGX_PRIORITY_SCHEDULING)
 #define SUPPORT_SGX_PRIORITY_SCHEDULING
@@ -245,3 +269,6 @@ must be defined when SGX_FEATURE_MP is defined
 
 #include "img_types.h"
 
+/******************************************************************************
+ End of file (sgxfeaturedefs.h)
+******************************************************************************/
index 1b265f1..a6a907a 100644 (file)
@@ -1,40 +1,61 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX MMU defines
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provides SGX MMU declarations and macros
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined(__SGXMMU_KM_H__)
 #define __SGXMMU_KM_H__
 
+/* to be implemented */
+
+/* SGX MMU maps 4Kb pages */
 #define SGX_MMU_PAGE_SHIFT                             (12)
 #define SGX_MMU_PAGE_SIZE                              (1U<<SGX_MMU_PAGE_SHIFT)
 #define SGX_MMU_PAGE_MASK                              (SGX_MMU_PAGE_SIZE - 1U)
 
+/* PD details */
 #define SGX_MMU_PD_SHIFT                               (10)
 #define SGX_MMU_PD_SIZE                                        (1U<<SGX_MMU_PD_SHIFT)
 #define SGX_MMU_PD_MASK                                        (0xFFC00000U)
 
+/* PD Entry details */
 #if defined(SGX_FEATURE_36BIT_MMU)
        #define SGX_MMU_PDE_ADDR_MASK                   (0xFFFFFF00U)
        #define SGX_MMU_PDE_ADDR_ALIGNSHIFT             (4)
@@ -43,6 +64,7 @@
        #define SGX_MMU_PDE_ADDR_ALIGNSHIFT             (0)
 #endif
 #define SGX_MMU_PDE_VALID                              (0x00000001U)
+/* variable page size control field */
 #define SGX_MMU_PDE_PAGE_SIZE_4K               (0x00000000U)
 #define SGX_MMU_PDE_PAGE_SIZE_16K              (0x00000002U)
 #define SGX_MMU_PDE_PAGE_SIZE_64K              (0x00000004U)
 #define SGX_MMU_PDE_PAGE_SIZE_4M               (0x0000000AU)
 #define SGX_MMU_PDE_PAGE_SIZE_MASK             (0x0000000EU)
 
+/* PT details */
 #define SGX_MMU_PT_SHIFT                               (10)
 #define SGX_MMU_PT_SIZE                                        (1U<<SGX_MMU_PT_SHIFT)
 #define SGX_MMU_PT_MASK                                        (0x003FF000U)
 
+/* PT Entry details */
 #if defined(SGX_FEATURE_36BIT_MMU)
        #define SGX_MMU_PTE_ADDR_MASK                   (0xFFFFFF00U)
        #define SGX_MMU_PTE_ADDR_ALIGNSHIFT             (4)
@@ -68,5 +92,8 @@
 #define SGX_MMU_PTE_CACHECONSISTENT            (0x00000008U)
 #define SGX_MMU_PTE_EDMPROTECT                 (0x00000010U)
 
-#endif 
+#endif /* __SGXMMU_KM_H__ */
 
+/*****************************************************************************
+ End of file (sgxmmu.h)
+*****************************************************************************/
index e34561a..4b9649f 100644 (file)
@@ -1,32 +1,48 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Hardware defs for SGXMP.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
 
-#ifndef _SGXMPDEFS_H_
-#define _SGXMPDEFS_H_
+The contents of this file are subject to the MIT license as set out below.
 
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+#ifndef _SGXMPDEFS_KM_H_
+#define _SGXMPDEFS_KM_H_
+
+/* Register EUR_CR_MASTER_BIF_CTRL */
 #define EUR_CR_MASTER_BIF_CTRL              0x4C00
 #define EUR_CR_MASTER_BIF_CTRL_NOREORDER_MASK 0x00000001U
 #define EUR_CR_MASTER_BIF_CTRL_NOREORDER_SHIFT 0
@@ -49,6 +65,7 @@
 #define EUR_CR_MASTER_BIF_CTRL_MMU_BYPASS_MASTER_DPM_MASK 0x00080000U
 #define EUR_CR_MASTER_BIF_CTRL_MMU_BYPASS_MASTER_DPM_SHIFT 19
 #define EUR_CR_MASTER_BIF_CTRL_MMU_BYPASS_MASTER_DPM_SIGNED 0
+/* Register EUR_CR_MASTER_BIF_CTRL_INVAL */
 #define EUR_CR_MASTER_BIF_CTRL_INVAL        0x4C34
 #define EUR_CR_MASTER_BIF_CTRL_INVAL_PTE_MASK 0x00000004U
 #define EUR_CR_MASTER_BIF_CTRL_INVAL_PTE_SHIFT 2
@@ -56,6 +73,7 @@
 #define EUR_CR_MASTER_BIF_CTRL_INVAL_ALL_MASK 0x00000008U
 #define EUR_CR_MASTER_BIF_CTRL_INVAL_ALL_SHIFT 3
 #define EUR_CR_MASTER_BIF_CTRL_INVAL_ALL_SIGNED 0
+/* Register EUR_CR_MASTER_BIF_MMU_CTRL */
 #define EUR_CR_MASTER_BIF_MMU_CTRL          0x4CD0
 #define EUR_CR_MASTER_BIF_MMU_CTRL_PREFETCHING_ON_MASK 0x00000001U
 #define EUR_CR_MASTER_BIF_MMU_CTRL_PREFETCHING_ON_SHIFT 0
@@ -66,6 +84,7 @@
 #define EUR_CR_MASTER_BIF_MMU_CTRL_ENABLE_DC_TLB_MASK 0x00000010U
 #define EUR_CR_MASTER_BIF_MMU_CTRL_ENABLE_DC_TLB_SHIFT 4
 #define EUR_CR_MASTER_BIF_MMU_CTRL_ENABLE_DC_TLB_SIGNED 0
+/* Register EUR_CR_MASTER_SLC_CTRL */
 #define EUR_CR_MASTER_SLC_CTRL              0x4D00
 #define EUR_CR_MASTER_SLC_CTRL_DISABLE_REORDERING_MASK 0x00800000U
 #define EUR_CR_MASTER_SLC_CTRL_DISABLE_REORDERING_SHIFT 23
 #define EUR_CR_MASTER_SLC_CTRL_PAUSE_MASK   0x00000100U
 #define EUR_CR_MASTER_SLC_CTRL_PAUSE_SHIFT  8
 #define EUR_CR_MASTER_SLC_CTRL_PAUSE_SIGNED 0
+/* Register EUR_CR_MASTER_SLC_CTRL_BYPASS */
 #define EUR_CR_MASTER_SLC_CTRL_BYPASS       0x4D04
 #define EUR_CR_MASTER_SLC_CTRL_BYPASS_BYP_CC_N_MASK 0x08000000U
 #define EUR_CR_MASTER_SLC_CTRL_BYPASS_BYP_CC_N_SHIFT 27
 #define EUR_CR_MASTER_SLC_CTRL_BYPASS_ALL_MASK 0x00000001U
 #define EUR_CR_MASTER_SLC_CTRL_BYPASS_ALL_SHIFT 0
 #define EUR_CR_MASTER_SLC_CTRL_BYPASS_ALL_SIGNED 0
+/* Register EUR_CR_MASTER_SLC_CTRL_USSE_INVAL */
 #define EUR_CR_MASTER_SLC_CTRL_USSE_INVAL   0x4D08
 #define EUR_CR_MASTER_SLC_CTRL_USSE_INVAL_ADDR_MASK 0xFFFFFFFFU
 #define EUR_CR_MASTER_SLC_CTRL_USSE_INVAL_ADDR_SHIFT 0
 #define EUR_CR_MASTER_SLC_CTRL_USSE_INVAL_ADDR_SIGNED 0
+/* Register EUR_CR_MASTER_SLC_CTRL_INVAL */
 #define EUR_CR_MASTER_SLC_CTRL_INVAL        0x4D28
 #define EUR_CR_MASTER_SLC_CTRL_INVAL_DM_EVENT_MASK 0x00000008U
 #define EUR_CR_MASTER_SLC_CTRL_INVAL_DM_EVENT_SHIFT 3
 #define EUR_CR_MASTER_SLC_CTRL_INVAL_ALL_MASK 0x00000001U
 #define EUR_CR_MASTER_SLC_CTRL_INVAL_ALL_SHIFT 0
 #define EUR_CR_MASTER_SLC_CTRL_INVAL_ALL_SIGNED 0
+/* Register EUR_CR_MASTER_SLC_CTRL_FLUSH */
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH        0x4D2C
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_DM_EVENT_MASK 0x00000080U
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_DM_EVENT_SHIFT 7
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_ALL_MASK 0x00000010U
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_ALL_SHIFT 4
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_ALL_SIGNED 0
+/* Register EUR_CR_MASTER_SLC_CTRL_FLUSH_INV */
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_INV    0x4D34
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_INV_DM_EVENT_MASK 0x00000080U
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_INV_DM_EVENT_SHIFT 7
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_INV_ALL_MASK 0x00000010U
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_INV_ALL_SHIFT 4
 #define EUR_CR_MASTER_SLC_CTRL_FLUSH_INV_ALL_SIGNED 0
+/* Register EUR_CR_MASTER_BREAKPOINT_READ */
 #define EUR_CR_MASTER_BREAKPOINT_READ       0x4F18
 #define EUR_CR_MASTER_BREAKPOINT_READ_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_MASTER_BREAKPOINT_READ_ADDRESS_SHIFT 4
 #define EUR_CR_MASTER_BREAKPOINT_READ_ADDRESS_SIGNED 0
+/* Register EUR_CR_MASTER_BREAKPOINT_TRAP */
 #define EUR_CR_MASTER_BREAKPOINT_TRAP       0x4F1C
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_CONTINUE_MASK 0x00000002U
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_CONTINUE_SHIFT 1
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_WRNOTIFY_MASK 0x00000001U
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_WRNOTIFY_SHIFT 0
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_WRNOTIFY_SIGNED 0
+/* Register EUR_CR_MASTER_BREAKPOINT */
 #define EUR_CR_MASTER_BREAKPOINT            0x4F20
 #define EUR_CR_MASTER_BREAKPOINT_ID_MASK    0x00000030U
 #define EUR_CR_MASTER_BREAKPOINT_ID_SHIFT   4
 #define EUR_CR_MASTER_BREAKPOINT_TRAPPED_MASK 0x00000004U
 #define EUR_CR_MASTER_BREAKPOINT_TRAPPED_SHIFT 2
 #define EUR_CR_MASTER_BREAKPOINT_TRAPPED_SIGNED 0
+/* Register EUR_CR_MASTER_BREAKPOINT_TRAP_INFO0 */
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO0 0x4F24
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO0_ADDRESS_MASK 0xFFFFFFF0U
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO0_ADDRESS_SHIFT 4
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO0_ADDRESS_SIGNED 0
+/* Register EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1 */
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1 0x4F28
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1_SIZE_MASK 0x00007C00U
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1_SIZE_SHIFT 10
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1_RNW_MASK 0x00000001U
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1_RNW_SHIFT 0
 #define EUR_CR_MASTER_BREAKPOINT_TRAP_INFO1_RNW_SIGNED 0
+/* Register EUR_CR_MASTER_CORE */
 #define EUR_CR_MASTER_CORE                  0x4000
 #define EUR_CR_MASTER_CORE_ENABLE_MASK      0x00000003U
 #define EUR_CR_MASTER_CORE_ENABLE_SHIFT     0
 #define EUR_CR_MASTER_CORE_ENABLE_SIGNED    0
+/* Register EUR_CR_MASTER_CORE_ID */
 #define EUR_CR_MASTER_CORE_ID               0x4010
 #define EUR_CR_MASTER_CORE_ID_CONFIG_MULTI_MASK 0x00000001U
 #define EUR_CR_MASTER_CORE_ID_CONFIG_MULTI_SHIFT 0
 #define EUR_CR_MASTER_CORE_ID_ID_MASK       0xFFFF0000U
 #define EUR_CR_MASTER_CORE_ID_ID_SHIFT      16
 #define EUR_CR_MASTER_CORE_ID_ID_SIGNED     0
+/* Register EUR_CR_MASTER_CORE_REVISION */
 #define EUR_CR_MASTER_CORE_REVISION         0x4014
 #define EUR_CR_MASTER_CORE_REVISION_MAINTENANCE_MASK 0x000000FFU
 #define EUR_CR_MASTER_CORE_REVISION_MAINTENANCE_SHIFT 0
 #define EUR_CR_MASTER_CORE_REVISION_DESIGNER_MASK 0xFF000000U
 #define EUR_CR_MASTER_CORE_REVISION_DESIGNER_SHIFT 24
 #define EUR_CR_MASTER_CORE_REVISION_DESIGNER_SIGNED 0
+/* Register EUR_CR_MASTER_SOFT_RESET */
 #define EUR_CR_MASTER_SOFT_RESET            0x4080
 #define EUR_CR_MASTER_SOFT_RESET_CORE_RESET_MASK(i) (0x00000001U << (0 + ((i) * 1)))
 #define EUR_CR_MASTER_SOFT_RESET_CORE_RESET_SHIFT(i) (0 + ((i) * 1))
 #define EUR_CR_MASTER_SOFT_RESET_PTLA_RESET_SHIFT 10
 #define EUR_CR_MASTER_SOFT_RESET_PTLA_RESET_SIGNED 0
 
-#endif 
+#endif /* _SGXMPDEFS_KM_H_ */
 
index ca26628..510f47d 100644 (file)
@@ -1,28 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Buffer Management.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Manages buffers mapped into two virtual memory spaces, host and
+                device and referenced by handles.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _BUFFER_MANAGER_H_
 #define _BUFFER_MANAGER_H_
 extern "C"{
 #endif
 
+/* forward reference */
 typedef struct _BM_HEAP_ BM_HEAP;
 
+/*
+ * The mapping structure is used to record relations between CPU virtual,
+ * CPU physical and device virtual addresses for large chunks of memory
+ * from which we have resource-allocator draw our buffers.
+ *
+ * There is one per contiguous pool and one per import from the host OS.
+ */
 struct _BM_MAPPING_
 {
        enum
        {
-               hm_wrapped = 1,         
-               hm_wrapped_scatter,     
-               hm_wrapped_virtaddr, 
-               hm_wrapped_scatter_virtaddr, 
-               hm_env,                         
-               hm_contiguous           
+               hm_wrapped = 1,         /*!< wrapped user supplied contiguous*/
+               hm_wrapped_scatter,     /*!< wrapped user supplied scattered */
+               hm_wrapped_virtaddr, /*!< wrapped user supplied contiguous with virtual address*/
+               hm_wrapped_scatter_virtaddr, /*!< wrapped user supplied scattered with virtual address*/
+               hm_env,                         /*!< obtained from environment */
+               hm_contiguous           /*!< contigous arena */
        } eCpuMemoryOrigin;
 
-       BM_HEAP                         *pBMHeap;       
-       RA_ARENA                        *pArena;        
+       BM_HEAP                         *pBMHeap;       /* which BM heap */
+       RA_ARENA                        *pArena;        /* whence the memory comes */
 
        IMG_CPU_VIRTADDR        CpuVAddr;
        IMG_CPU_PHYADDR         CpuPAddr;
        IMG_DEV_VIRTADDR        DevVAddr;
        IMG_SYS_PHYADDR         *psSysAddr;
        IMG_SIZE_T                      uSize;
+       IMG_SIZE_T                      uSizeVM;
     IMG_HANDLE          hOSMemHandle;
        IMG_UINT32                      ui32Flags;
+
+       /* Sparse mapping data */
+       IMG_UINT32                      ui32ChunkSize;
+       IMG_UINT32                      ui32NumVirtChunks;
+       IMG_UINT32                      ui32NumPhysChunks;
+       IMG_BOOL                        *pabMapChunk;
 };
 
+/*
+ * The buffer structure handles individual allocations from the user; thus
+ * there is one allocated per call to BM_Alloc and one per call to BM_Wrap.
+ * We record a mapping reference so we know where to return allocated
+ * resources at BM_Free time.
+ */
 typedef struct _BM_BUF_
 {
        IMG_CPU_VIRTADDR        *CpuVAddr;
@@ -86,45 +124,101 @@ struct _BM_HEAP_
        
        struct _BM_HEAP_                *psNext;
        struct _BM_HEAP_                **ppsThis;
+       /* BIF tile stride for this heap */
+       IMG_UINT32                              ui32XTileStride;
 };
 
+/*
+ * The bm-context structure
+ */
 struct _BM_CONTEXT_
 {
        MMU_CONTEXT     *psMMUContext;
 
-       
+       /*
+        * Resource allocation arena of dual mapped pages. For devices
+        * where the hardware imposes different constraints on the valid
+        * device virtual address range depending on the use of the buffer
+        * we maintain two allocation arenas, one low address range, the
+        * other high. For devices without such a constrain we do not
+        * create the high arena, instead all allocations come from the
+        * low arena.
+        */
         BM_HEAP *psBMHeap;
 
-       
+       /*
+        * The Shared Heaps
+        */
         BM_HEAP *psBMSharedHeap;
 
        PVRSRV_DEVICE_NODE *psDeviceNode;
 
-       
+       /*
+        * Hash table management.
+        */
        HASH_TABLE *pBufferHash;
 
-       
+       /*
+        *      Resman item handle
+        */
        IMG_HANDLE hResItem;
 
        IMG_UINT32 ui32RefCount;
 
-       
-
+       /*
+               linked list next pointer
+       */
        struct _BM_CONTEXT_ *psNext;
        struct _BM_CONTEXT_ **ppsThis;
 };
 
-
-
+/* refcount.c needs to know the internals of this structure */
+typedef struct _XPROC_DATA_{
+       IMG_UINT32 ui32RefCount;
+       IMG_UINT32 ui32AllocFlags;
+       IMG_UINT32 ui32Size;
+       IMG_UINT32 ui32PageSize;
+    RA_ARENA *psArena;
+    IMG_SYS_PHYADDR sSysPAddr;
+       IMG_VOID *pvCpuVAddr;
+       IMG_HANDLE hOSMemHandle;
+} XPROC_DATA;
+
+extern XPROC_DATA gXProcWorkaroundShareData[];
+/*
+       Buffer handle.
+*/
 typedef IMG_VOID *BM_HANDLE;
 
+/** Buffer manager allocation flags.
+ *
+ *  Flags passed to BM_Alloc to specify buffer capabilities.
+ *
+ * @defgroup BP Buffer Manager Allocation Flags
+ * @{
+ */
+
+/** Pool number mask. */
 #define BP_POOL_MASK         0x7
 
+/* Request physically contiguous pages of memory */
 #define BP_CONTIGUOUS                  (1 << 3)
 #define BP_PARAMBUFFER                 (1 << 4)
 
 #define BM_MAX_DEVMEM_ARENAS  2
 
+/** @} */
+
+/**
+ *  @Function BM_CreateContext
+ *
+ *  @Description
+ *
+ *  @Input
+
+ *  @Return
+ */
+
 IMG_HANDLE
 BM_CreateContext(PVRSRV_DEVICE_NODE                    *psDeviceNode,
                                 IMG_DEV_PHYADDR                        *psPDDevPAddr,
@@ -132,30 +226,113 @@ BM_CreateContext(PVRSRV_DEVICE_NODE                      *psDeviceNode,
                                 IMG_BOOL                                       *pbCreated);
 
 
+/**
+ *  @Function   BM_DestroyContext
+ *
+ *  @Description
+ *
+ *  @Input
+ *
+ *  @Return PVRSRV_ERROR
+ */
 PVRSRV_ERROR
 BM_DestroyContext (IMG_HANDLE hBMContext,
                                        IMG_BOOL *pbCreated);
 
 
+/**
+ *  @Function   BM_CreateHeap
+ *
+ *  @Description
+ *
+ *  @Input
+ *
+ *  @Return
+ */
 IMG_HANDLE
 BM_CreateHeap (IMG_HANDLE hBMContext,
                                DEVICE_MEMORY_HEAP_INFO *psDevMemHeapInfo);
 
+/**
+ *  @Function   BM_DestroyHeap
+ *
+ *  @Description
+ *
+ *  @Input
+ *
+ *  @Return
+ */
 IMG_VOID
 BM_DestroyHeap (IMG_HANDLE hDevMemHeap);
 
 
+/**
+ *  @Function   BM_Reinitialise
+ *
+ *  @Description
+ *
+ *  Reinitialises the buffer manager after a power event. Calling this
+ *  function will reprogram MMU registers and renable the MMU.
+ *
+ *  @Input None
+ *  @Return None
+ */
+
 IMG_BOOL
 BM_Reinitialise (PVRSRV_DEVICE_NODE *psDeviceNode);
 
+/**
+ *  @Function   BM_Alloc
+ *
+ *  @Description
+ *
+ *  Allocate a buffer mapped into both host and device virtual memory
+ *  maps.
+ *
+ *  @Input uSize - require size in bytes of the buffer.
+ *  @Input/Output pui32Flags - bit mask of buffer property flags + recieves heap flags.
+ *  @Input uDevVAddrAlignment - required alignment in bytes, or 0.
+ *  @Input pvPrivData - private data passed to OS allocator
+ *  @Input ui32PrivDataLength - length of private data
+ *  @Input ui32ChunkSize - Chunk size
+ *  @Input ui32NumVirtChunks - Number of virtual chunks
+ *  @Input ui32NumPhysChunks - Number of physical chunks
+ *  @Input pabMapChunk - Chunk mapping array
+ *  @Output phBuf - receives the buffer handle.
+ *  @Return IMG_TRUE - Success, IMG_FALSE - Failed.
+ */
 IMG_BOOL
 BM_Alloc (IMG_HANDLE                   hDevMemHeap,
                        IMG_DEV_VIRTADDR        *psDevVAddr,
                        IMG_SIZE_T                      uSize,
                        IMG_UINT32                      *pui32Flags,
                        IMG_UINT32                      uDevVAddrAlignment,
+                       IMG_PVOID                       pvPrivData,
+                       IMG_UINT32                      ui32PrivDataLength,
+                       IMG_UINT32                      ui32ChunkSize,
+                       IMG_UINT32                      ui32NumVirtChunks,
+                       IMG_UINT32                      ui32NumPhysChunks,
+                       IMG_BOOL                        *pabMapChunk,
                        BM_HANDLE                       *phBuf);
 
+/**
+ *  @Function   BM_Wrap
+ *
+ *  @Description
+ *
+ *  Create a buffer which wraps user provided host physical memory.
+ *  The wrapped memory must be page aligned. BM_Wrap will roundup the
+ *  size to a multiple of host pages.
+ *
+ *  @Input ui32Size - size of memory to wrap.
+ *  @Input ui32Offset - Offset into page of memory to wrap.
+ *  @Input bPhysContig - Is the wrap physically contiguous.
+ *  @Input psSysAddr - list of system physical page addresses of memory to wrap.
+ *     @Input pvCPUVAddr - optional CPU kernel virtual address (Page aligned) of memory to wrap.
+ *  @Input uFlags - bit mask of buffer property flags.
+ *  @Input phBuf - receives the buffer handle.
+ *  @Return IMG_TRUE - Success, IMG_FALSE - Failed
+ */
 IMG_BOOL
 BM_Wrap (      IMG_HANDLE hDevMemHeap,
                    IMG_SIZE_T ui32Size,
@@ -166,50 +343,280 @@ BM_Wrap (        IMG_HANDLE hDevMemHeap,
                        IMG_UINT32 *pui32Flags,
                        BM_HANDLE *phBuf);
 
+/**
+ *  @Function   BM_Free
+ *
+ *  @Description
+ *
+ *  Free a buffer previously allocated via BM_Alloc.
+ *
+ *  @Input  hBuf - buffer handle.
+ *  @Return None.
+ */
 IMG_VOID
 BM_Free (BM_HANDLE hBuf,
                IMG_UINT32 ui32Flags);
 
 
+/**
+ *  @Function   BM_HandleToCpuVaddr
+ *
+ *  @Description
+ *
+ *  Retrieve the host virtual address associated with a buffer.
+ *
+ *  @Input  hBuf - buffer handle.
+ *
+ *  @Return buffers host virtual address.
+ */
 IMG_CPU_VIRTADDR
 BM_HandleToCpuVaddr (BM_HANDLE hBuf);
 
+/**
+ *  @Function   BM_HandleToDevVaddr
+ *
+ *  @Description
+ *
+ *  Retrieve the device virtual address associated with a buffer.
+ *
+ *  @Input hBuf - buffer handle.
+ *  @Return buffers device virtual address.
+ */
 IMG_DEV_VIRTADDR
 BM_HandleToDevVaddr (BM_HANDLE hBuf);
 
+/**
+ *  @Function   BM_HandleToSysPaddr
+ *
+ *  @Description
+ *
+ *  Retrieve the system physical address associated with a buffer.
+ *
+ *  @Input hBuf - buffer handle.
+ *  @Return buffers device virtual address.
+ */
 IMG_SYS_PHYADDR
 BM_HandleToSysPaddr (BM_HANDLE hBuf);
 
+/**
+ *  @Function   BM_HandleToMemOSHandle
+ *
+ *  @Description
+ *
+ *  Retrieve the underlying memory handle associated with a buffer.
+ *
+ *  @Input hBuf - buffer handle.
+ *  @Return An OS Specific memory handle
+ */
 IMG_HANDLE
 BM_HandleToOSMemHandle (BM_HANDLE hBuf);
 
+/**
+ *  @Function   BM_GetPhysPageAddr
+ *
+ *  @Description
+ *
+ *  Retreive physical address backing dev V address
+ *
+ *  @Input psMemInfo
+ *  @Input sDevVPageAddr
+ *  @Output psDevPAddr
+ *  @Return PVRSRV_ERROR
+ */
 IMG_VOID BM_GetPhysPageAddr(PVRSRV_KERNEL_MEM_INFO *psMemInfo,
                                                                IMG_DEV_VIRTADDR sDevVPageAddr,
                                                                IMG_DEV_PHYADDR *psDevPAddr);
 
+/*!
+******************************************************************************
+ @Function             BM_GetMMUContext
+
+ @Description
+                               utility function to return the MMU context
+
+ @inputs        hDevMemHeap - the Dev mem heap handle
+
+ @Return               MMU context, else NULL
+**************************************************************************/
 MMU_CONTEXT* BM_GetMMUContext(IMG_HANDLE hDevMemHeap);
 
+/*!
+******************************************************************************
+ @Function             BM_GetMMUContextFromMemContext
+
+ @Description
+                               utility function to return the MMU context
+
+ @inputs        hDevMemHeap - the Dev mem heap handle
+
+ @Return               MMU context, else NULL
+**************************************************************************/
 MMU_CONTEXT* BM_GetMMUContextFromMemContext(IMG_HANDLE hDevMemContext);
 
+/*!
+******************************************************************************
+ @Function             BM_GetMMUHeap
+
+ @Description
+                               utility function to return the MMU heap handle
+
+ @inputs        hDevMemHeap - the Dev mem heap handle
+
+ @Return               MMU heap handle, else NULL
+**************************************************************************/
 IMG_HANDLE BM_GetMMUHeap(IMG_HANDLE hDevMemHeap);
 
+/*!
+******************************************************************************
+ @Function             BM_GetDeviceNode
+
+ @Description  utility function to return the devicenode from the BM Context
+
+ @inputs        hDevMemContext - the Dev Mem Context
+
+ @Return               MMU heap handle, else NULL
+**************************************************************************/
 PVRSRV_DEVICE_NODE* BM_GetDeviceNode(IMG_HANDLE hDevMemContext);
 
 
+/*!
+******************************************************************************
+ @Function             BM_GetMappingHandle
+
+ @Description  utility function to return the mapping handle from a meminfo
+
+ @inputs        psMemInfo - kernel meminfo
+
+ @Return               mapping handle, else NULL
+**************************************************************************/
 IMG_HANDLE BM_GetMappingHandle(PVRSRV_KERNEL_MEM_INFO *psMemInfo);
 
+/*!
+******************************************************************************
+ @Function             BM_Export
+
+ @Description  Export a buffer previously allocated via BM_Alloc.
+
+ @inputs        hBuf - buffer handle.
+
+ @Return               None.
+**************************************************************************/
 IMG_VOID BM_Export(BM_HANDLE hBuf);
 
+/*!
+******************************************************************************
+ @Function             BM_FreeExport
+
+ @Description  Free a buffer previously exported via BM_Export.
+
+ @inputs        hBuf - buffer handle.
+                ui32Flags - flags
+
+ @Return               None.
+**************************************************************************/
 IMG_VOID BM_FreeExport(BM_HANDLE hBuf, IMG_UINT32 ui32Flags);
 
+/*!
+******************************************************************************
+ @Function     BM_MappingHandleFromBuffer
+
+ @Description  utility function to get the BM mapping handle from a BM buffer
+
+ @Input     hBuffer - Handle to BM buffer
+
+ @Return       BM mapping handle
+**************************************************************************/
+IMG_HANDLE BM_MappingHandleFromBuffer(IMG_HANDLE hBuffer);
+
+/*!
+******************************************************************************
+ @Function     BM_GetVirtualSize
+
+ @Description  utility function to get the VM size of a BM mapping
+
+ @Input     hBMHandle - Handle to BM mapping
+
+ @Return       VM size of mapping
+**************************************************************************/
+IMG_UINT32 BM_GetVirtualSize(IMG_HANDLE hBMHandle);
+
+/*!
+******************************************************************************
+ @Function     BM_MapPageAtOffset
+
+ @Description  utility function check if the specificed offset in a BM mapping
+                is a page that needs tp be mapped
+
+ @Input     hBMHandle - Handle to BM mapping
+
+ @Input     ui32Offset - Offset into import
+
+ @Return       IMG_TRUE if the page should be mapped
+**************************************************************************/
+IMG_BOOL BM_MapPageAtOffset(IMG_HANDLE hBMHandle, IMG_UINT32 ui32Offset);
+
+/*!
+******************************************************************************
+ @Function     BM_VirtOffsetToPhyscial
+
+ @Description  utility function find of physical offset of a sparse allocation
+                from it's virtual offset.
+
+ @Input     hBMHandle - Handle to BM mapping
+
+ @Input     ui32VirtOffset - Virtual offset into allocation
+ @Output    pui32PhysOffset - Physical offset
+
+ @Return       IMG_TRUE if the virtual offset is physically backed
+**************************************************************************/
+IMG_BOOL BM_VirtOffsetToPhysical(IMG_HANDLE hBMHandle,
+                                                                  IMG_UINT32 ui32VirtOffset,
+                                                                  IMG_UINT32 *pui32PhysOffset);
+
+/* The following are present for the "share mem" workaround for
+   cross-process mapping.  This is only valid for a specific
+   use-case, and only tested on Linux (Android) and only
+   superficially at that.  Do not rely on this API! */
+/* The two "Set" functions set a piece of "global" state in the buffer
+   manager, and "Unset" removes this global state.  Therefore, there
+   is no thread-safety here and it's the caller's responsibility to
+   ensure that a mutex is acquired before using these functions or any
+   device memory allocation functions, including, especially,
+   callbacks from RA. */
+/* Once a "Share Index" is set by this means, any requests from the RA
+   to import a block of physical memory shall cause the physical
+   memory allocation to be refcounted, and shared iff the IDs chosen
+   match */
+/* This API is difficult to use, but saves a lot of plumbing in other
+   APIs.  The next generation of this library should have this functionality 
+   plumbed in properly */
 PVRSRV_ERROR BM_XProcWorkaroundSetShareIndex(IMG_UINT32 ui32Index);
 PVRSRV_ERROR BM_XProcWorkaroundUnsetShareIndex(IMG_UINT32 ui32Index);
 PVRSRV_ERROR BM_XProcWorkaroundFindNewBufferAndSetShareIndex(IMG_UINT32 *pui32Index);
-IMG_UINT32 BM_XProcWorkaroundGetRefCount(IMG_UINT32 ui32Index);
+
+#if defined(PVRSRV_REFCOUNT_DEBUG)
+IMG_VOID _BM_XProcIndexAcquireDebug(const IMG_CHAR *pszFile, IMG_INT iLine, IMG_UINT32 ui32Index);
+IMG_VOID _BM_XProcIndexReleaseDebug(const IMG_CHAR *pszFile, IMG_INT iLine, IMG_UINT32 ui32Index);
+
+#define BM_XProcIndexAcquire(x...) \
+       _BM_XProcIndexAcquireDebug(__FILE__, __LINE__, x)
+#define BM_XProcIndexRelease(x...) \
+       _BM_XProcIndexReleaseDebug(__FILE__, __LINE__, x)
+
+#else
+IMG_VOID _BM_XProcIndexAcquire(IMG_UINT32 ui32Index);
+IMG_VOID _BM_XProcIndexRelease(IMG_UINT32 ui32Index);
+
+#define BM_XProcIndexAcquire(x) \
+       _BM_XProcIndexAcquire( x)
+#define BM_XProcIndexRelease(x) \
+       _BM_XProcIndexRelease( x)
+#endif
+
 
 #if defined(__cplusplus)
 }
 #endif
 
 #endif
-
index 9df2c73..6ddee5d 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Common Device header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Device related function templates and defines
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __DEVICE_H__
 #define __DEVICE_H__
 extern "C" {
 #endif
        
-#include "ra.h"                
-#include "resman.h"            
+#include "ra.h"                /* RA_ARENA */
+#include "resman.h"            /* PRESMAN_ITEM */
 
+/* BM context forward reference */
 typedef struct _BM_CONTEXT_ BM_CONTEXT;
 
+/* pre-defined MMU structure forward references */
 typedef struct _MMU_HEAP_ MMU_HEAP;
 typedef struct _MMU_CONTEXT_ MMU_CONTEXT;
 
+/* physical resource types: */
+/* contiguous system memory */
 #define PVRSRV_BACKINGSTORE_SYSMEM_CONTIG              (1<<(PVRSRV_MEM_BACKINGSTORE_FIELD_SHIFT+0))
+/* non-contiguous system memory */
 #define PVRSRV_BACKINGSTORE_SYSMEM_NONCONTIG   (1<<(PVRSRV_MEM_BACKINGSTORE_FIELD_SHIFT+1))
+/* contiguous local device memory */
 #define PVRSRV_BACKINGSTORE_LOCALMEM_CONTIG            (1<<(PVRSRV_MEM_BACKINGSTORE_FIELD_SHIFT+2))
+/* non-contiguous local device memory */
 #define PVRSRV_BACKINGSTORE_LOCALMEM_NONCONTIG (1<<(PVRSRV_MEM_BACKINGSTORE_FIELD_SHIFT+3))
 
+/* heap types: */
 typedef IMG_UINT32 DEVICE_MEMORY_HEAP_TYPE;
 #define DEVICE_MEMORY_HEAP_PERCONTEXT          0
 #define DEVICE_MEMORY_HEAP_KERNEL                      1
@@ -51,38 +75,38 @@ typedef IMG_UINT32 DEVICE_MEMORY_HEAP_TYPE;
 #define DEVICE_MEMORY_HEAP_SHARED_EXPORTED     3
 
 #define PVRSRV_DEVICE_NODE_FLAGS_PORT80DISPLAY 1
-#define PVRSRV_DEVICE_NODE_FLAGS_MMU_OPT_INV   2       
+#define PVRSRV_DEVICE_NODE_FLAGS_MMU_OPT_INV   2       /* FIXME : Optimal Invalidation is not default */
 
 typedef struct _DEVICE_MEMORY_HEAP_INFO_
 {
-       
+       /* heap identifier */
        IMG_UINT32                              ui32HeapID;
 
-       
+       /* heap identifier string */
        IMG_CHAR                                *pszName;
 
-       
+       /* backing store identifier string */
        IMG_CHAR                                *pszBSName;
        
-       
+       /* Device virtual address of base of heap */
        IMG_DEV_VIRTADDR                sDevVAddrBase;
 
-       
+       /* heapsize in bytes */
        IMG_UINT32                              ui32HeapSize;
 
-       
+       /* Flags, includes physical resource (backing store type). Must be available to SOC */
        IMG_UINT32                              ui32Attribs;
 
-       
+       /* Heap type: per device, kernel only, shared, shared_exported */
        DEVICE_MEMORY_HEAP_TYPE DevMemHeapType;
        
-       
+       /* kernel heap handle */
        IMG_HANDLE                              hDevMemHeap;
        
-       
+       /* ptr to local memory allocator for this heap */
        RA_ARENA                                *psLocalDevMemArena;
 
-       
+       /* MMU data page size (4kb, 16kb, 256kb, 1Mb, 4Mb) */
        IMG_UINT32                              ui32DataPageSize;
 
        IMG_UINT32                              ui32XTileStride;
@@ -91,48 +115,56 @@ typedef struct _DEVICE_MEMORY_HEAP_INFO_
 
 typedef struct _DEVICE_MEMORY_INFO_
 {
-       
+       /* size of address space, as log2 */
        IMG_UINT32                              ui32AddressSpaceSizeLog2;
 
-       
-
-
+       /* 
+               flags, includes physical memory resource types available to the system.  
+               Allows for validation at heap creation, define PVRSRV_BACKINGSTORE_XXX 
+       */
        IMG_UINT32                              ui32Flags;
 
-       
+       /* heap count.  Doesn't include additional heaps from PVRSRVCreateDeviceMemHeap */
        IMG_UINT32                              ui32HeapCount;
        
-       
+       /* the sync heap id - common code needs to know */
        IMG_UINT32                              ui32SyncHeapID;
        
-       
+       /* heap for buffer mappings  */
        IMG_UINT32                              ui32MappingHeapID;
 
-       
+       /* heap for ion buffers  */
+       IMG_UINT32                              ui32IonHeapID;
+
+       /* device memory heap info about each heap in a device address space */
        DEVICE_MEMORY_HEAP_INFO *psDeviceMemoryHeap;
 
-       
+       /* BM kernel context for the device */
     BM_CONTEXT                         *pBMKernelContext;
 
-       
+       /* BM context list for the device*/
     BM_CONTEXT                         *pBMContext;
 
 } DEVICE_MEMORY_INFO;
 
 
+/*!
+ ****************************************************************************
+       Device memory descriptor for a given system
+ ****************************************************************************/
 typedef struct DEV_ARENA_DESCRIPTOR_TAG
 {
-       IMG_UINT32                              ui32HeapID;             
+       IMG_UINT32                              ui32HeapID;             /*!< memory pool has a unique id for diagnostic purposes */
 
-       IMG_CHAR                                *pszName;               
+       IMG_CHAR                                *pszName;               /*!< memory pool has a unique string for diagnostic purposes */
 
-       IMG_DEV_VIRTADDR                BaseDevVAddr;   
+       IMG_DEV_VIRTADDR                BaseDevVAddr;   /*!< Device virtual base address of the managed memory pool. */
 
-       IMG_UINT32                              ui32Size;               
+       IMG_UINT32                              ui32Size;               /*!< Size in bytes of the managed memory pool. */
 
-       DEVICE_MEMORY_HEAP_TYPE DevMemHeapType;
+       DEVICE_MEMORY_HEAP_TYPE DevMemHeapType;/*!< heap type */
 
-       
+       /* MMU data page size (4kb, 16kb, 256kb, 1Mb, 4Mb) */
        IMG_UINT32                              ui32DataPageSize;
 
        DEVICE_MEMORY_HEAP_INFO *psDeviceMemoryHeapInfo;
@@ -140,26 +172,30 @@ typedef struct DEV_ARENA_DESCRIPTOR_TAG
 } DEV_ARENA_DESCRIPTOR;
 
 
+/*
+       PDUMP MMU atttributes
+*/
 typedef struct _PDUMP_MMU_ATTRIB_
 {
        PVRSRV_DEVICE_IDENTIFIER        sDevId;
        
        IMG_CHAR        *pszPDRegRegion;
        
-       
+       /* data page info */
        IMG_UINT32 ui32DataPageMask;
 
-       
+       /* page table info */
        IMG_UINT32 ui32PTEValid;
        IMG_UINT32 ui32PTSize;
        IMG_UINT32 ui32PTEAlignShift;
 
-       
+       /* page directory info */
        IMG_UINT32 ui32PDEMask;
        IMG_UINT32 ui32PDEAlignShift;
 
 } PDUMP_MMU_ATTRIB;
 
+/* forward reference to _SYS_DATA_ */
 typedef struct _SYS_DATA_TAG_ *PSYS_DATA;
 
 typedef struct _PVRSRV_DEVICE_NODE_
@@ -167,17 +203,18 @@ typedef struct _PVRSRV_DEVICE_NODE_
        PVRSRV_DEVICE_IDENTIFIER        sDevId;
        IMG_UINT32                                      ui32RefCount;
 
-       
-
-       
+       /*
+               callbacks the device must support:
+       */
+       /* device initialiser */
        PVRSRV_ERROR                    (*pfnInitDevice) (IMG_VOID*);
-       
+       /* device deinitialiser */
        PVRSRV_ERROR                    (*pfnDeInitDevice) (IMG_VOID*);
 
-       
+       /* device post-finalise compatibility check */
        PVRSRV_ERROR                    (*pfnInitDeviceCompatCheck) (struct _PVRSRV_DEVICE_NODE_*);
 
-       
+       /* device MMU interface */
        PVRSRV_ERROR                    (*pfnMMUInitialise)(struct _PVRSRV_DEVICE_NODE_*, MMU_CONTEXT**, IMG_DEV_PHYADDR*);
        IMG_VOID                                (*pfnMMUFinalise)(MMU_CONTEXT*);
        IMG_VOID                                (*pfnMMUInsertHeap)(MMU_CONTEXT*, MMU_HEAP*);
@@ -198,6 +235,16 @@ typedef struct _PVRSRV_DEVICE_NODE_
                                                                                          IMG_SIZE_T uSize,
                                                                                          IMG_UINT32 ui32MemFlags,
                                                                                          IMG_HANDLE hUniqueTag);
+       IMG_VOID                                (*pfnMMUMapPagesSparse)(MMU_HEAP *pMMU,
+                                                                                                       IMG_DEV_VIRTADDR devVAddr,
+                                                                                                       IMG_SYS_PHYADDR SysPAddr,
+                                                                                                       IMG_UINT32 ui32ChunkSize,
+                                                                                                       IMG_UINT32 ui32NumVirtChunks,
+                                                                                                       IMG_UINT32 ui32NumPhysChunks,
+                                                                                                       IMG_BOOL *pabMapChunk,
+                                                                                                       IMG_UINT32 ui32MemFlags,
+                                                                                                       IMG_HANDLE hUniqueTag);
+
        IMG_VOID                                (*pfnMMUMapShadow)(MMU_HEAP            *pMMU,
                                                                                           IMG_DEV_VIRTADDR    MapBaseDevVAddr,
                                                                                           IMG_SIZE_T          uSize, 
@@ -206,6 +253,18 @@ typedef struct _PVRSRV_DEVICE_NODE_
                                                                                           IMG_DEV_VIRTADDR    *pDevVAddr,
                                                                                           IMG_UINT32 ui32MemFlags,
                                                                                           IMG_HANDLE hUniqueTag);
+       IMG_VOID                                (*pfnMMUMapShadowSparse)(MMU_HEAP            *pMMU,
+                                                                                                        IMG_DEV_VIRTADDR    MapBaseDevVAddr,
+                                                                                                        IMG_UINT32          ui32ChunkSize,
+                                                                                                        IMG_UINT32          ui32NumVirtChunks,
+                                                                                                        IMG_UINT32          ui32NumPhysChunks,
+                                                                                                        IMG_BOOL            *pabMapChunk,
+                                                                                                        IMG_CPU_VIRTADDR    CpuVAddr,
+                                                                                                        IMG_HANDLE          hOSMemHandle,
+                                                                                                        IMG_DEV_VIRTADDR    *pDevVAddr,
+                                                                                                        IMG_UINT32          ui32MemFlags,
+                                                                                                        IMG_HANDLE          hUniqueTag);
+
        IMG_VOID                                (*pfnMMUUnmapPages)(MMU_HEAP *pMMU,
                                                                                                IMG_DEV_VIRTADDR dev_vaddr,
                                                                                                IMG_UINT32 ui32PageCount,
@@ -225,7 +284,7 @@ typedef struct _PVRSRV_DEVICE_NODE_
        IMG_VOID                                (*pfnMMUGetCacheFlushRange)(MMU_CONTEXT *pMMUContext, IMG_UINT32 *pui32RangeMask);
        IMG_VOID                                (*pfnMMUGetPDPhysAddr)(MMU_CONTEXT *pMMUContext, IMG_DEV_PHYADDR *psDevPAddr);
 
-       
+       /* tiling range control functions */
        PVRSRV_ERROR                    (*pfnAllocMemTilingRange)(struct _PVRSRV_DEVICE_NODE_ *psDeviceNode,
                                                                                                                PVRSRV_KERNEL_MEM_INFO *psMemInfo,
                                                                                                                IMG_UINT32 ui32TilingStride,
@@ -233,36 +292,36 @@ typedef struct _PVRSRV_DEVICE_NODE_
        PVRSRV_ERROR                    (*pfnFreeMemTilingRange)(struct _PVRSRV_DEVICE_NODE_ *psDeviceNode,
                                                                                                                IMG_UINT32 ui32RangeIndex);
 
-       
+       /* LISR handler for device */
        IMG_BOOL                                (*pfnDeviceISR)(IMG_VOID*);
-       
+       /* ISR data */
        IMG_VOID                                *pvISRData;
-       
+       /* System/SOC specific interrupt bit relating to this device */
        IMG_UINT32                              ui32SOCInterruptBit;
-       
+       /* MISR handler for device */
        IMG_VOID                                (*pfnDeviceMISR)(IMG_VOID*);
 
-       
+       /* Software command complete callback for device */
        IMG_VOID                                (*pfnDeviceCommandComplete)(struct _PVRSRV_DEVICE_NODE_ *psDeviceNode);
-       
+       /* Flag indicating that command complete callback needs to be reprocessed */
        IMG_BOOL                                bReProcessDeviceCommandComplete;
 
        IMG_VOID                                (*pfnCacheInvalidate)(struct _PVRSRV_DEVICE_NODE_ *psDeviceNode);
 
-       
+       /* information about the device's address space and heaps */
        DEVICE_MEMORY_INFO              sDevMemoryInfo;
 
-       
+       /* private device information */
        IMG_VOID                                *pvDevice;
-       IMG_UINT32                              ui32pvDeviceSize; 
+       IMG_UINT32                              ui32pvDeviceSize; /* required by GetClassDeviceInfo API */
                
-       
+       /* Resource Manager Context */
        PRESMAN_CONTEXT                 hResManContext;
        
-       
+       /* pointer back to parent sysdata */
        PSYS_DATA                               psSysData;
        
-       
+       /* default MMU PT/PD backing store to use for the device */
        RA_ARENA                                *psLocalDevMemArena;
        
        IMG_UINT32                              ui32Flags;
@@ -271,9 +330,11 @@ typedef struct _PVRSRV_DEVICE_NODE_
        struct _PVRSRV_DEVICE_NODE_     **ppsThis;
        
 #if defined(PDUMP)
-       
+       /*      device-level callback which is called when pdump.exe starts.
+        *      Should be implemented in device-specific init code, e.g. sgxinit.c
+        */
        PVRSRV_ERROR                    (*pfnPDumpInitDevice)(struct _PVRSRV_DEVICE_NODE_ *psDeviceNode);
-       
+       /* device-level callback to return pdump ID associated to a memory context */
        IMG_UINT32                              (*pfnMMUGetContextID)(IMG_HANDLE hDevMemContext);
 #endif
 } PVRSRV_DEVICE_NODE;
@@ -292,23 +353,45 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVDeinitialiseDevice(IMG_UINT32 ui32DevIndex);
 
 #if !defined(USE_CODE)
 
-IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PollForValueKM(volatile IMG_UINT32*       pui32LinMemAddr,
-                                                                                                       IMG_UINT32                              ui32Value,
-                                                                                                       IMG_UINT32                              ui32Mask,
-                                                                                                       IMG_UINT32                              ui32Timeoutus,
-                                                                                                       IMG_UINT32                              ui32PollPeriodus,
-                                                                                                       IMG_BOOL                                bAllowPreemption);
+/*!
+******************************************************************************
 
-#endif 
+ @Function     PollForValueKM
+
+ @Description
+ Polls for a value to match a masked read of sysmem
+
+ @Input pui32LinMemAddr : CPU linear address of the mem to poll
+ @Input ui32Value : req'd value
+ @Input ui32Mask : Mask
+ @Input ui32Timeoutus : maximum total time to wait (us)
+ @Input ui32PollPeriodus : minimum delay between consecutive polls (us)
+ @Input bAllowPreemption : allow the polling loop to be preempted
+
+ @Return   PVRSRV_ERROR :
+
+******************************************************************************/
+IMG_IMPORT PVRSRV_ERROR IMG_CALLCONV PollForValueKM(volatile IMG_UINT32*  pui32LinMemAddr,
+                                                    IMG_UINT32            ui32Value,
+                                                    IMG_UINT32            ui32Mask,
+                                                    IMG_UINT32            ui32Timeoutus,
+                                                    IMG_UINT32            ui32PollPeriodus,
+                                                    IMG_BOOL              bAllowPreemption);
+
+#endif /* !defined(USE_CODE) */
 
 
 #if defined (USING_ISR_INTERRUPTS)
 PVRSRV_ERROR IMG_CALLCONV PollForInterruptKM(IMG_UINT32 ui32Value,
-                                                               IMG_UINT32 ui32Mask,
-                                                               IMG_UINT32 ui32Waitus,
-                                                               IMG_UINT32 ui32Tries);
-#endif 
+                                             IMG_UINT32 ui32Mask,
+                                             IMG_UINT32 ui32Waitus,
+                                             IMG_UINT32 ui32Tries);
+
+#endif /* #if defined (USING_ISR_INTERRUPTS) */
 
+/* The following functions don't really belong here (srvkm.h might be a better 
+ * place), but as they use the device data structures, this is the most convenient 
+ * place for them. */
 PVRSRV_ERROR IMG_CALLCONV PVRSRVInit(PSYS_DATA psSysData);
 IMG_VOID IMG_CALLCONV PVRSRVDeInit(PSYS_DATA psSysData);
 IMG_BOOL IMG_CALLCONV PVRSRVDeviceLISR(PVRSRV_DEVICE_NODE *psDeviceNode);
@@ -319,5 +402,8 @@ IMG_VOID IMG_CALLCONV PVRSRVMISR(IMG_VOID *pvSysData);
 }
 #endif
        
-#endif 
+#endif /* __DEVICE_H__ */
 
+/******************************************************************************
+ End of file (device.h)
+******************************************************************************/
index 536fa56..157d209 100644 (file)
-/**********************************************************************
+/*************************************************************************/ /*!
+@Title          Handle Manager API
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description   Provide handle management
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+#ifndef __HANDLE_H__
+#define __HANDLE_H__
+
+/*
+ * Handle API
+ * ----------
+ * The handle API is intended to provide handles for kernel resources,
+ * which can then be passed back to user space processes.
  *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
+ * The following functions comprise the API.  Each function takes a
+ * pointer to a PVRSRV_HANDLE_BASE strcture, one of which is allocated
+ * for each process, and stored in the per-process data area.  Use
+ * KERNEL_HANDLE_BASE for handles not allocated for a particular process,
+ * or for handles that need to be allocated before the PVRSRV_HANDLE_BASE
+ * structure for the process is available.
  *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+ * PVRSRV_ERROR PVRSRVAllocHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_HANDLE *phHandle, IMG_VOID *pvData, PVRSRV_HANDLE_TYPE eType,
+ *     PVRSRV_HANDLE_ALLOC_FLAG eFlag);
  *
- ******************************************************************************/
-
-#ifndef __HANDLE_H__
-#define __HANDLE_H__
+ * Allocate a handle phHandle, for the resource of type eType pointed to by
+ * pvData.
+ *
+ * For handles that have a definite lifetime, where the corresponding
+ * resource is explicitly created and destroyed, eFlag should be zero.
+ *
+ * If the resource is not explicitly created and destroyed, eFlag should be
+ * set to PVRSRV_HANDLE_ALLOC_FLAG_SHARED.  For a given process, the same
+ * handle will be returned each time a handle for the resource is allocated
+ * with the PVRSRV_HANDLE_ALLOC_FLAG_SHARED flag.
+ *
+ * If a particular resource may be referenced multiple times by a
+ * given process, setting eFlag to PVRSRV_HANDLE_ALLOC_FLAG_MULTI
+ * will allow multiple handles to be allocated for the resource.
+ * Such handles cannot be found with PVRSRVFindHandle.
+ *
+ * PVRSRV_ERROR PVRSRVAllocSubHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_HANDLE *phHandle, IMG_VOID *pvData, PVRSRV_HANDLE_TYPE eType,
+ *     PVRSRV_HANDLE_ALLOC_FLAG eFlag, IMG_HANDLE hParent);
+ *
+ * This function is similar to PVRSRVAllocHandle, except that the allocated
+ * handles are associated with a parent handle, hParent, that has been
+ * allocated previously.  Subhandles are automatically deallocated when their
+ * parent handle is dealloacted.
+ * Subhandles can be treated as ordinary handles.  For example, they may
+ * have subhandles of their own, and may be explicity deallocated using
+ * PVRSRVReleaseHandle (see below).
+ *
+ * PVRSRV_ERROR PVRSRVFindHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_HANDLE *phHandle, IMG_VOID *pvData, PVRSRV_HANDLE_TYPE eType);
+ *
+ * Find the handle previously allocated for the resource pointed to by
+ * pvData, of type eType.  Handles allocated with the flag
+ * PVRSRV_HANDLE_ALLOC_FLAG_MULTI cannot be found using this
+ * function.
+ *
+ * PVRSRV_ERROR PVRSRVLookupHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_PVOID *ppvData, IMG_HANDLE hHandle, PVRSRV_HANDLE_TYPE eType);
+ *
+ * Given a handle for a resource of type eType, return the pointer to the
+ * resource.
+ *
+ * PVRSRV_ERROR PVRSRVLookuSubHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_PVOID *ppvData, IMG_HANDLE hHandle, PVRSRV_HANDLE_TYPE eType,
+ *     IMH_HANDLE hAncestor);
+ *
+ * Similar to PVRSRVLookupHandle, but checks the handle is a descendent
+ * of hAncestor.
+ *
+ * PVRSRV_ERROR PVRSRVLookupHandleAnyType(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_PVOID *ppvData, PVRSRV_HANDLE_TYPE *peType, IMG_HANDLE hHandle);
+ *
+ * This function returns the resource pointer corresponding to the
+ * given handle, and the resource type in peType.  This function is
+ * intended for situations where a handle may be one of several types,
+ * but the type isn't known beforehand.
+ *
+ * PVRSRV_ERROR PVRSRVReleaseHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_HANDLE hHandle, PVRSRV_HANDLE_TYPE eType);
+ *
+ * Deallocate a handle of given type.
+ *
+ * PVRSRV_ERROR PVRSRVLookupAndReleaseHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_PVOID *ppvData, IMG_HANDLE hHandle, PVRSRV_HANDLE_TYPE eType);
+ *
+ * This function combines the functionality of PVRSRVLookupHandle and
+ * PVRSRVReleaseHandle, deallocating the handle after looking it up.
+ *
+ * PVRSRV_ERROR PVRSRVGetParentHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_PVOID *phParent, IMG_HANDLE hHandle, PVRSRV_HANDLE_TYPE eType);
+ *
+ * Return the parent of a handle in *phParent, or IMG_NULL if the handle has
+ * no parent.
+ *
+ * PVRSRV_ERROR PVRSRVNewHandleBatch(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_UINT32 ui32BatchSize)
+ *
+ * Allocate a new handle batch.  This preallocates ui32BatchSize handles.
+ * Batch mode simplifies the handling of handle allocation failures.
+ * The handle API is unchanged in batch mode, except that handles freed
+ * in batch mode will not be available for reallocation until the batch
+ * is committed or released (see below).
+ *
+ * PVRSRV_ERROR PVRSRVCommitHandleBatch(PVRSRV_HANDLE_BASE *psBase)
+ * void PVRSRVReleaseHandleBatch(PVRSRV_HANDLE_BASE *psBase)
+ *
+ * When handle allocation from a handle batch is complete, the
+ * batch must be committed by calling PVRSRVCommitHandleBatch.  If
+ * an error occurred, and none of the handles in the batch are no
+ * longer needed, PVRSRVReleaseHandleBatch must be called.
+ * The macros PVRSRVAllocHandleNR, and PVRSRVAllocSubHandleNR
+ * are defined for use in batch mode.  These work the same way
+ * as PVRSRVAllocHandle and PVRSRVAllocSubHandle, except that
+ * they don't return a value, relying on the fact that
+ * PVRSRVCommitHandleBatch will not commit any of the handles
+ * in a batch if there was an error allocating one of the
+ * handles in the batch.
+ *
+ * PVRSRV_ERROR PVRSRVSetMaxHandle(PVRSRV_HANDLE_BASE *psBase,
+ *     IMG_UINT32 ui32MaxHandle)
+ * Set the maximum handle number.  This is intended to restrict the
+ * handle range so that it will fit within a given field width.  For
+ * example, setting the maximum handle number to 0x7fffffff, would
+ * ensure the handles would fit within a 31 bit width field.  This
+ * facility should be used with caution, as it restricts the number of
+ * handles that can be allocated.
+ *
+ * IMG_UINT32 PVRSRVGetMaxHandle(PVRSRV_HANDLE_BASE *psBase)
+ * Return the maximum handle number, or 0 if the setting of a limit
+ * is not supported.
+ *
+ * PVRSRV_ERROR PVRSRVEnableHandlePurging(PVRSRV_HANDLE_BASE *psBase)
+ * Allows unused handle space to be reclaimed, by calling
+ * PVRSRVPurgeHandles.  Note that allocating handles may have a
+ * higher overhead if purging is enabled.
+ *
+ * PVRSRV_ERROR PVRSRVPurgeHandles((PVRSRV_HANDLE_BASE *psBase)
+ * Purge handles for a handle base that has purging enabled.
+ */
 
 #if defined (__cplusplus)
 extern "C" {
@@ -65,13 +217,13 @@ typedef enum
 
 typedef enum
 {
-       
+       /* No flags */
        PVRSRV_HANDLE_ALLOC_FLAG_NONE =                 0,
-       
+       /* Share a handle that already exists for a given data pointer */
        PVRSRV_HANDLE_ALLOC_FLAG_SHARED =               0x01,
-       
+       /* Muliple handles can point at the given data pointer */
        PVRSRV_HANDLE_ALLOC_FLAG_MULTI =                0x02,
-       
+       /* Subhandles are allocated in a private handle space */
        PVRSRV_HANDLE_ALLOC_FLAG_PRIVATE =              0x04
 } PVRSRV_HANDLE_ALLOC_FLAG;
 
@@ -119,7 +271,7 @@ PVRSRV_ERROR PVRSRVGetParentHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *phPare
 PVRSRV_ERROR PVRSRVLookupAndReleaseHandle(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvData, IMG_HANDLE hHandle, PVRSRV_HANDLE_TYPE eType);
 
 PVRSRV_ERROR PVRSRVReleaseHandle(PVRSRV_HANDLE_BASE *psBase, IMG_HANDLE hHandle, PVRSRV_HANDLE_TYPE eType);
-#endif 
+#endif /* #if defined (SUPPORT_SID_INTERFACE) */
 
 PVRSRV_ERROR PVRSRVNewHandleBatch(PVRSRV_HANDLE_BASE *psBase, IMG_UINT32 ui32BatchSize);
 
@@ -143,7 +295,7 @@ PVRSRV_ERROR PVRSRVHandleInit(IMG_VOID);
 
 PVRSRV_ERROR PVRSRVHandleDeInit(IMG_VOID);
 
-#else  
+#else  /* #if defined (PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)*/
 
 #define KERNEL_HANDLE_BASE IMG_NULL
 
@@ -196,7 +348,10 @@ static INLINE
 PVRSRV_ERROR PVRSRVLookupHandleAnyType(PVRSRV_HANDLE_BASE *psBase, IMG_PVOID *ppvData, PVRSRV_HANDLE_TYPE *peType, IMG_HANDLE hHandle)
 {
        PVR_UNREFERENCED_PARAMETER(psBase);
-       
+       /*
+        * Unlike the other functions here, the returned results will need
+        * to be handled differently for the secure and non-secure cases.
+        */
        *peType = PVRSRV_HANDLE_TYPE_NONE;
 
        *ppvData = hHandle;
@@ -388,8 +543,13 @@ PVRSRV_ERROR PVRSRVHandleDeInit(IMG_VOID)
        return PVRSRV_OK;
 }
 
-#endif 
+#endif /* #if defined (PVR_SECURE_HANDLES) || defined (SUPPORT_SID_INTERFACE)*/
 
+/*
+ * Versions of PVRSRVAllocHandle and PVRSRVAllocSubHandle with no return
+ * values.  Intended for use with batched handle allocation, relying on
+ * CommitHandleBatch to detect handle allocation errors.
+ */
 #define PVRSRVAllocHandleNR(psBase, phHandle, pvData, eType, eFlag) \
        (IMG_VOID)PVRSRVAllocHandle(psBase, phHandle, pvData, eType, eFlag)
 
@@ -400,5 +560,8 @@ PVRSRV_ERROR PVRSRVHandleDeInit(IMG_VOID)
 }
 #endif
 
-#endif 
+#endif /* __HANDLE_H__ */
 
+/******************************************************************************
+ End of file (handle.h)
+******************************************************************************/
index 3662089..1ed6fd0 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Self scaling hash tables
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Implements simple self scaling hash tables.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _HASH_H_
 #define _HASH_H_
 extern "C" {
 #endif
 
+/*
+ * Keys passed to the comparsion function are only guaranteed to
+ * be aligned on an IMG_UINTPTR_T boundary. 
+ */
 typedef IMG_UINT32 HASH_FUNC(IMG_SIZE_T uKeySize, IMG_VOID *pKey, IMG_UINT32 uHashTabLen);
 typedef IMG_BOOL HASH_KEY_COMP(IMG_SIZE_T uKeySize, IMG_VOID *pKey1, IMG_VOID *pKey2);
 
@@ -44,31 +64,203 @@ typedef PVRSRV_ERROR (*HASH_pfnCallback) (
        IMG_UINTPTR_T v
 );
 
+/*!
+******************************************************************************
+    @Function       HASH_Func_Default
+
+    @Description    Hash function intended for hashing keys composed of
+                    IMG_UINTPTR_T arrays.
+                               
+    @Input          uKeySize - the size of the hash key, in bytes.
+    @Input          pKey - a pointer to the key to hash.
+    @Input          uHashTabLen - the length of the hash table. 
+
+    @Return         The hash value.
+******************************************************************************/
 IMG_UINT32 HASH_Func_Default (IMG_SIZE_T uKeySize, IMG_VOID *pKey, IMG_UINT32 uHashTabLen);
 
+/*!
+******************************************************************************
+    @Function       HASH_Key_Comp_Default
+
+    @Description    Compares keys composed of IMG_UINTPTR_T arrays.
+                               
+    @Input          uKeySize - the size of the hash key, in bytes.
+    @Input          pKey1 - pointer to first hash key to compare.
+    @Input          pKey2 - pointer to second hash key to compare.
+
+    @Return         IMG_TRUE  - the keys match.
+                    IMG_FALSE - the keys don't match.
+******************************************************************************/
 IMG_BOOL HASH_Key_Comp_Default (IMG_SIZE_T uKeySize, IMG_VOID *pKey1, IMG_VOID *pKey2);
 
+/*!
+******************************************************************************
+    @Function       HASH_Create_Extended
+
+    @Description    Create a self scaling hash table, using the supplied
+                    key size, and the supllied hash and key comparsion
+                    functions.
+                               
+    @Input          uInitialLen - initial and minimum length of the
+                        hash table, where the length refers to the number
+                        of entries in the hash table, not its size in
+                        bytes.
+    @Input          uKeySize - the size of the key, in bytes.
+    @Input          pfnHashFunc - pointer to hash function.
+    @Input          pfnKeyComp - pointer to key comparsion function.
+
+    @Return         IMG_NULL or hash table handle.
+******************************************************************************/
 HASH_TABLE * HASH_Create_Extended (IMG_UINT32 uInitialLen, IMG_SIZE_T uKeySize, HASH_FUNC *pfnHashFunc, HASH_KEY_COMP *pfnKeyComp);
 
+/*!
+******************************************************************************
+    @Function       HASH_Create
+
+    @Description    Create a self scaling hash table with a key
+                    consisting of a single IMG_UINTPTR_T, and using
+                    the default hash and key comparison functions.
+                               
+    @Input          uInitialLen - initial and minimum length of the
+                        hash table, where the length refers to the
+                        number of entries in the hash table, not its size
+                        in bytes.
+
+    @Return         IMG_NULL or hash table handle.
+******************************************************************************/
 HASH_TABLE * HASH_Create (IMG_UINT32 uInitialLen);
 
+/*!
+******************************************************************************
+    @Function       HASH_Delete
+
+    @Description    Delete a hash table created by HASH_Create_Extended or
+                    HASH_Create.  All entries in the table must have been
+                    removed before calling this function.
+                               
+    @Input          pHash - hash table
+
+    @Return         None
+******************************************************************************/
 IMG_VOID HASH_Delete (HASH_TABLE *pHash);
 
+/*!
+******************************************************************************
+    @Function       HASH_Insert_Extended
+
+    @Description    Insert a key value pair into a hash table created
+                    with HASH_Create_Extended.
+                               
+    @Input          pHash - the hash table.
+    @Input          pKey - pointer to the key.
+    @Input          v - the value associated with the key.
+
+    @Return         IMG_TRUE - success.
+                    IMG_FALSE - failure.
+******************************************************************************/
 IMG_BOOL HASH_Insert_Extended (HASH_TABLE *pHash, IMG_VOID *pKey, IMG_UINTPTR_T v);
 
+/*!
+******************************************************************************
+    @Function       HASH_Insert
+
+    @Description    Insert a key value pair into a hash table created with
+                    HASH_Create.
+                               
+    @Input          pHash - the hash table.
+    @Input          k - the key value.
+    @Input          v - the value associated with the key.
+
+    @Return         IMG_TRUE - success.
+                    IMG_FALSE - failure.
+******************************************************************************/
 IMG_BOOL HASH_Insert (HASH_TABLE *pHash, IMG_UINTPTR_T k, IMG_UINTPTR_T v);
 
+/*!
+******************************************************************************
+    @Function       HASH_Remove_Extended
+
+    @Description    Remove a key from a hash table created with
+                    HASH_Create_Extended.
+                               
+    @Input          pHash - the hash table.
+    @Input          pKey - pointer to key.
+
+    @Return         0 if the key is missing, or the value associated
+                    with the key.
+******************************************************************************/
 IMG_UINTPTR_T HASH_Remove_Extended(HASH_TABLE *pHash, IMG_VOID *pKey);
 
+/*!
+******************************************************************************
+    @Function       HASH_Remove
+
+    @Description    Remove a key value pair from a hash table created
+                    with HASH_Create.
+                               
+    @Input          pHash - the hash table
+    @Input          k - the key
+
+    @Return         0 if the key is missing, or the value associated
+                    with the key.
+******************************************************************************/
 IMG_UINTPTR_T HASH_Remove (HASH_TABLE *pHash, IMG_UINTPTR_T k);
 
+/*!
+******************************************************************************
+    @Function       HASH_Retrieve_Extended
+
+    @Description    Retrieve a value from a hash table created with
+                    HASH_Create_Extended.
+                               
+    @Input          pHash - the hash table.
+    @Input          pKey - pointer to the key.
+
+    @Return         0 if the key is missing, or the value associated with
+                    the key.
+******************************************************************************/
 IMG_UINTPTR_T HASH_Retrieve_Extended (HASH_TABLE *pHash, IMG_VOID *pKey);
 
+/*!
+******************************************************************************
+    @Function       HASH_Retrieve
+
+    @Description    Retrieve a value from a hash table created with
+                    HASH_Create.
+                               
+    @Input          pHash - the hash table
+    @Input          k - the key
+
+    @Return         0 if the key is missing, or the value associated with
+                    the key.
+******************************************************************************/
 IMG_UINTPTR_T HASH_Retrieve (HASH_TABLE *pHash, IMG_UINTPTR_T k);
 
+/*!
+******************************************************************************
+    @Function       HASH_Interate
+
+    @Description    Iterate over every entry in the hash table
+
+    @Input          pHash - the old hash table
+    @Input          HASH_pfnCallback - the size of the old hash table
+
+    @Return         Callback error if any, otherwise PVRSRV_OK
+******************************************************************************/
 PVRSRV_ERROR HASH_Iterate(HASH_TABLE *pHash, HASH_pfnCallback pfnCallback);
 
 #ifdef HASH_TRACE
+/*!
+******************************************************************************
+    @Function       HASH_Dump
+
+    @Description    Dump out some information about a hash table.
+                               
+    @Input          pHash - the hash table
+
+    @Return         None
+******************************************************************************/
 IMG_VOID HASH_Dump (HASH_TABLE *pHash);
 #endif
 
@@ -76,5 +268,10 @@ IMG_VOID HASH_Dump (HASH_TABLE *pHash);
 }
 #endif
 
-#endif 
+#endif /* _HASH_H_ */
+
+/******************************************************************************
+ End of file (hash.h)
+******************************************************************************/
+
 
index a02307a..81205de 100644 (file)
@@ -1,35 +1,90 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Linked list shared functions templates.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Definition of the linked list function templates.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __LISTS_UTILS__
 #define __LISTS_UTILS__
 
+/* instruct QAC to ignore warnings about the following custom formatted macros */
+/* PRQA S 0881,3410 ++ */
 #include <stdarg.h>
 #include "img_types.h"
 
+/*
+ - USAGE -
+
+ The list functions work with any structure that provides the fields psNext and
+ ppsThis. In order to make a function available for a given type, it is required
+ to use the funcion template macro that creates the actual code.
+
+ There are 4 main types of functions:
+ - INSERT      : given a pointer to the head pointer of the list and a pointer to
+                         the node, inserts it as the new head.
+ - REMOVE      : given a pointer to a node, removes it from its list.
+ - FOR EACH    : apply a function over all the elements of a list.
+ - ANY         : apply a function over the elements of a list, until one of them
+                         return a non null value, and then returns it.
+
+ The two last functions can have a variable argument form, with allows to pass
+ additional parameters to the callback function. In order to do this, the
+ callback function must take two arguments, the first is the current node and
+ the second is a list of variable arguments (va_list).
+
+ The ANY functions have also another for wich specifies the return type of the
+ callback function and the default value returned by the callback function.
+
+*/
+
+/*!
+******************************************************************************
+    @Function       List_##TYPE##_ForEach
+
+    @Description    Apply a callback function to all the elements of a list.
+
+    @Input          psHead - the head of the list to be processed.
+    @Input          pfnCallBack - the function to be applied to each element 
+                        of the list.
+
+    @Return         None
+******************************************************************************/
 #define DECLARE_LIST_FOR_EACH(TYPE) \
 IMG_VOID List_##TYPE##_ForEach(TYPE *psHead, IMG_VOID(*pfnCallBack)(TYPE* psNode))
 
@@ -61,6 +116,19 @@ IMG_VOID List_##TYPE##_ForEach_va(TYPE *psHead, IMG_VOID(*pfnCallBack)(TYPE* psN
 }
 
 
+/*!
+******************************************************************************
+    @Function       List_##TYPE##_Any
+
+    @Description    Applies a callback function to the elements of a list until 
+                    the function returns a non null value, then returns it.
+
+    @Input          psHead - the head of the list to be processed.
+    @Input          pfnCallBack - the function to be applied to each element 
+                    of the list.
+
+    @Return         None
+******************************************************************************/
 #define DECLARE_LIST_ANY(TYPE) \
 IMG_VOID* List_##TYPE##_Any(TYPE *psHead, IMG_VOID* (*pfnCallBack)(TYPE* psNode))
 
@@ -81,6 +149,8 @@ IMG_VOID* List_##TYPE##_Any(TYPE *psHead, IMG_VOID* (*pfnCallBack)(TYPE* psNode)
 }
 
 
+/*with variable arguments, that will be passed as a va_list to the callback function*/
+
 #define DECLARE_LIST_ANY_VA(TYPE) \
 IMG_VOID* List_##TYPE##_Any_va(TYPE *psHead, IMG_VOID*(*pfnCallBack)(TYPE* psNode, va_list va), ...)
 
@@ -101,6 +171,8 @@ IMG_VOID* List_##TYPE##_Any_va(TYPE *psHead, IMG_VOID*(*pfnCallBack)(TYPE* psNod
        return pResult;\
 }
 
+/*those ones are for extra type safety, so there's no need to use castings for the results*/
+
 #define DECLARE_LIST_ANY_2(TYPE, RTYPE, CONTINUE) \
 RTYPE List_##TYPE##_##RTYPE##_Any(TYPE *psHead, RTYPE (*pfnCallBack)(TYPE* psNode))
 
@@ -142,6 +214,16 @@ RTYPE List_##TYPE##_##RTYPE##_Any_va(TYPE *psHead, RTYPE(*pfnCallBack)(TYPE* psN
 }
 
 
+/*!
+******************************************************************************
+    @Function       List_##TYPE##_Remove
+
+    @Description    Removes a given node from the list.
+
+    @Input          psNode - the pointer to the node to be removed.
+
+    @Return         None
+******************************************************************************/
 #define DECLARE_LIST_REMOVE(TYPE) \
 IMG_VOID List_##TYPE##_Remove(TYPE *psNode)
 
@@ -155,6 +237,17 @@ IMG_VOID List_##TYPE##_Remove(TYPE *psNode)\
        }\
 }
 
+/*!
+******************************************************************************
+    @Function       List_##TYPE##_Insert
+
+    @Description    Inserts a given node at the beginnning of the list.
+
+    @Input          psHead - The pointer to the pointer to the head node.
+    @Input          psNode - The pointer to the node to be inserted.
+
+    @Return         None
+******************************************************************************/
 #define DECLARE_LIST_INSERT(TYPE) \
 IMG_VOID List_##TYPE##_Insert(TYPE **ppsHead, TYPE *psNewNode)
 
@@ -170,6 +263,16 @@ IMG_VOID List_##TYPE##_Insert(TYPE **ppsHead, TYPE *psNewNode)\
        }\
 }
 
+/*!
+******************************************************************************
+    @Function       List_##TYPE##_Reverse
+
+    @Description    Reverse a list in place
+
+    @Input          ppsHead - The pointer to the pointer to the head node.
+                                       
+    @Return         None
+******************************************************************************/
 #define DECLARE_LIST_REVERSE(TYPE) \
 IMG_VOID List_##TYPE##_Reverse(TYPE **ppsHead)
 
@@ -242,3 +345,5 @@ IMG_VOID* MatchPowerDeviceIndex_AnyVaCb(PVRSRV_POWER_DEV *psPowerDev, va_list va
 
 #endif
 
+/* re-enable warnings */
+/* PRQA S 0881,3410 -- */
index 69e1b3d..18079cb 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Time measurement interface.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _METRICS_
 #define _METRICS_
@@ -90,21 +105,19 @@ extern IMG_VOID   PVRSRVOutputMetricTotals(IMG_VOID);
 
 #if defined(__sh__)
 
-#define TST_REG   ((volatile IMG_UINT8 *) (psDevInfo->pvSOCRegsBaseKM))        
+#define TST_REG   ((volatile IMG_UINT8 *) (psDevInfo->pvSOCRegsBaseKM))        // timer start register
 
-#define TCOR_2    ((volatile IMG_UINT *)  (psDevInfo->pvSOCRegsBaseKM+28))     
-#define TCNT_2    ((volatile IMG_UINT *)  (psDevInfo->pvSOCRegsBaseKM+32))     
-#define TCR_2     ((volatile IMG_UINT16 *)(psDevInfo->pvSOCRegsBaseKM+36))     
+#define TCOR_2    ((volatile IMG_UINT *)  (psDevInfo->pvSOCRegsBaseKM+28))     // timer constant register_2
+#define TCNT_2    ((volatile IMG_UINT *)  (psDevInfo->pvSOCRegsBaseKM+32))     // timer counter register_2
+#define TCR_2     ((volatile IMG_UINT16 *)(psDevInfo->pvSOCRegsBaseKM+36))     // timer control register_2
 
 #define TIMER_DIVISOR  4
 
-#endif 
+#endif /* defined(__sh__) */
 
 
 
-
-
-#else 
+#else /* defined(DEBUG) || defined(TIMING) */
 
 
 
@@ -119,12 +132,15 @@ extern IMG_VOID   PVRSRVOutputMetricTotals(IMG_VOID);
 
 
 
-#endif 
+#endif /* defined(DEBUG) || defined(TIMING) */
 
 #if defined(__cplusplus)
 }
 #endif
 
 
-#endif 
+#endif /* _METRICS_ */
 
+/**************************************************************************
+ End of file (metrics.h)
+**************************************************************************/
index b76cefd..34d3367 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          OS functions header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    OS specific API definitions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifdef DEBUG_RELEASE_BUILD
 #pragma optimize( "", off )
 #define DEBUG          1
@@ -46,9 +61,13 @@ extern "C" {
 #endif
 
 
-       
+/* setup conditional pageable / non-pageable select */
+       /* Non-Vista OSs only need pageable */
        #define PVRSRV_PAGEABLE_SELECT          PVRSRV_OS_PAGEABLE_HEAP
 
+/******************************************************************************
+ * Static defines
+ *****************************************************************************/
 #define KERNEL_ID                      0xffffffffL
 #define POWER_MANAGER_ID       0xfffffffeL
 #define ISR_ID                         0xfffffffdL
@@ -59,9 +78,12 @@ extern "C" {
 #define HOST_PAGEMASK                  (HOST_PAGESIZE()-1)
 #define HOST_PAGEALIGN(addr)   (((addr) + HOST_PAGEMASK) & ~HOST_PAGEMASK)
 
-#define PVRSRV_OS_HEAP_MASK                    0xf 
-#define PVRSRV_OS_PAGEABLE_HEAP                0x1 
-#define PVRSRV_OS_NON_PAGEABLE_HEAP    0x2 
+/******************************************************************************
+ *     Host memory heaps
+ *****************************************************************************/
+#define PVRSRV_OS_HEAP_MASK                    0xf /* host heap flags mask */
+#define PVRSRV_OS_PAGEABLE_HEAP                0x1 /* allocation pageable */
+#define PVRSRV_OS_NON_PAGEABLE_HEAP    0x2 /* allocation non pageable */
 
 
 IMG_UINT32 OSClockus(IMG_VOID);
@@ -80,9 +102,16 @@ IMG_VOID OSMemCopy(IMG_VOID *pvDst, IMG_VOID *pvSrc, IMG_SIZE_T ui32Size);
 IMG_VOID *OSMapPhysToLin(IMG_CPU_PHYADDR BasePAddr, IMG_SIZE_T ui32Bytes, IMG_UINT32 ui32Flags, IMG_HANDLE *phOSMemHandle);
 IMG_BOOL OSUnMapPhysToLin(IMG_VOID *pvLinAddr, IMG_SIZE_T ui32Bytes, IMG_UINT32 ui32Flags, IMG_HANDLE hOSMemHandle);
 
-PVRSRV_ERROR OSReservePhys(IMG_CPU_PHYADDR BasePAddr, IMG_SIZE_T ui32Bytes, IMG_UINT32 ui32Flags, IMG_VOID **ppvCpuVAddr, IMG_HANDLE *phOSMemHandle);
+PVRSRV_ERROR OSReservePhys(IMG_CPU_PHYADDR BasePAddr, IMG_SIZE_T ui32Bytes, IMG_UINT32 ui32Flags, IMG_HANDLE hBMHandle, IMG_VOID **ppvCpuVAddr, IMG_HANDLE *phOSMemHandle);
 PVRSRV_ERROR OSUnReservePhys(IMG_VOID *pvCpuVAddr, IMG_SIZE_T ui32Bytes, IMG_UINT32 ui32Flags, IMG_HANDLE hOSMemHandle);
 
+/* Some terminology:
+ *
+ *  FLUSH              Flush w/ invalidate
+ *  CLEAN              Flush w/o invalidate
+ *  INVALIDATE Invalidate w/o flush
+ */
+
 #if defined(__linux__) && defined(__KERNEL__)
 
 IMG_VOID OSFlushCPUCacheKM(IMG_VOID);
@@ -90,16 +119,19 @@ IMG_VOID OSFlushCPUCacheKM(IMG_VOID);
 IMG_VOID OSCleanCPUCacheKM(IMG_VOID);
 
 IMG_BOOL OSFlushCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                               IMG_UINT32 ui32ByteOffset,
                                                                IMG_VOID *pvRangeAddrStart,
                                                                IMG_UINT32 ui32Length);
 IMG_BOOL OSCleanCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                               IMG_UINT32 ui32ByteOffset,
                                                                IMG_VOID *pvRangeAddrStart,
                                                                IMG_UINT32 ui32Length);
 IMG_BOOL OSInvalidateCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                                        IMG_UINT32 ui32ByteOffset,
                                                                         IMG_VOID *pvRangeAddrStart,
                                                                         IMG_UINT32 ui32Length);
 
-#else 
+#else /* defined(__linux__) && defined(__KERNEL__) */
 
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(OSFlushCPUCacheKM)
@@ -115,10 +147,12 @@ static INLINE IMG_VOID OSCleanCPUCacheKM(IMG_VOID) {}
 #pragma inline(OSFlushCPUCacheRangeKM)
 #endif
 static INLINE IMG_BOOL OSFlushCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                                                         IMG_UINT32 ui32ByteOffset,
                                                                                          IMG_VOID *pvRangeAddrStart,
                                                                                          IMG_UINT32 ui32Length)
 {
        PVR_UNREFERENCED_PARAMETER(hOSMemHandle);
+       PVR_UNREFERENCED_PARAMETER(ui32ByteOffset);
        PVR_UNREFERENCED_PARAMETER(pvRangeAddrStart);
        PVR_UNREFERENCED_PARAMETER(ui32Length);
        return IMG_FALSE;
@@ -128,10 +162,12 @@ static INLINE IMG_BOOL OSFlushCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
 #pragma inline(OSCleanCPUCacheRangeKM)
 #endif
 static INLINE IMG_BOOL OSCleanCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                                                         IMG_UINT32 ui32ByteOffset,
                                                                                          IMG_VOID *pvRangeAddrStart,
                                                                                          IMG_UINT32 ui32Length)
 {
        PVR_UNREFERENCED_PARAMETER(hOSMemHandle);
+       PVR_UNREFERENCED_PARAMETER(ui32ByteOffset);
        PVR_UNREFERENCED_PARAMETER(pvRangeAddrStart);
        PVR_UNREFERENCED_PARAMETER(ui32Length);
        return IMG_FALSE;
@@ -141,18 +177,20 @@ static INLINE IMG_BOOL OSCleanCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
 #pragma inline(OSInvalidateCPUCacheRangeKM)
 #endif
 static INLINE IMG_BOOL OSInvalidateCPUCacheRangeKM(IMG_HANDLE hOSMemHandle,
+                                                                                                  IMG_UINT32 ui32ByteOffset,
                                                                                                   IMG_VOID *pvRangeAddrStart,
                                                                                                   IMG_UINT32 ui32Length)
 {
        PVR_UNREFERENCED_PARAMETER(hOSMemHandle);
+       PVR_UNREFERENCED_PARAMETER(ui32ByteOffset);
        PVR_UNREFERENCED_PARAMETER(pvRangeAddrStart);
        PVR_UNREFERENCED_PARAMETER(ui32Length);
        return IMG_FALSE;
 }
 
-#endif 
+#endif /* defined(__linux__) && defined(__KERNEL__) */
 
-#if (defined(__linux__) || defined(__QNXNTO__))
+#if defined(__linux__) || defined(__QNXNTO__)
 PVRSRV_ERROR OSRegisterDiscontigMem(IMG_SYS_PHYADDR *pBasePAddr,
                                                                        IMG_VOID *pvCpuVAddr, 
                                                                        IMG_SIZE_T ui32Bytes,
@@ -162,7 +200,7 @@ PVRSRV_ERROR OSUnRegisterDiscontigMem(IMG_VOID *pvCpuVAddr,
                                                                        IMG_SIZE_T ui32Bytes,
                                                                        IMG_UINT32 ui32Flags,
                                                                        IMG_HANDLE hOSMemHandle);
-#else  
+#else  /* defined(__linux__) */
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(OSRegisterDiscontigMem)
 #endif
@@ -196,10 +234,10 @@ static INLINE PVRSRV_ERROR OSUnRegisterDiscontigMem(IMG_VOID *pvCpuVAddr,
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
-#endif 
+#endif /* defined(__linux__) */
 
 
-#if (defined(__linux__) || defined(__QNXNTO__))
+#if  defined(__linux__) || defined(__QNXNTO__)
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(OSReserveDiscontigPhys)
 #endif
@@ -211,8 +249,16 @@ static INLINE PVRSRV_ERROR OSReserveDiscontigPhys(IMG_SYS_PHYADDR *pBasePAddr, I
 #else
        extern IMG_CPU_PHYADDR SysSysPAddrToCpuPAddr(IMG_SYS_PHYADDR SysPAddr);
 
-       
-       return OSReservePhys(SysSysPAddrToCpuPAddr(pBasePAddr[0]), ui32Bytes, ui32Flags, ppvCpuVAddr, phOSMemHandle);
+       /*
+        * On uITRON we know:
+        * 1. We will only be called with a non-contig physical if we
+        *    already have a contiguous CPU linear
+        * 2. There is a one->one mapping of CpuPAddr -> CpuVAddr
+        * 3. Looking up the first CpuPAddr will find the first CpuVAddr
+        * 4. We don't need to unmap
+        */
+
+       return OSReservePhys(SysSysPAddrToCpuPAddr(pBasePAddr[0]), ui32Bytes, ui32Flags, IMG_NULL, ppvCpuVAddr, phOSMemHandle);
 #endif 
 }
 
@@ -221,10 +267,10 @@ static INLINE PVRSRV_ERROR OSUnReserveDiscontigPhys(IMG_VOID *pvCpuVAddr, IMG_SI
 #if defined(__linux__) || defined(__QNXNTO__) 
        OSUnRegisterDiscontigMem(pvCpuVAddr, ui32Bytes, ui32Flags, hOSMemHandle);
 #endif
-       
+       /* We don't need to unmap */
        return PVRSRV_OK;
 }
-#else  
+#else  /* defined(__linux__) */
 
 
 #ifdef INLINE_IS_PRAGMA
@@ -253,7 +299,7 @@ static INLINE PVRSRV_ERROR OSUnReserveDiscontigPhys(IMG_VOID *pvCpuVAddr, IMG_SI
 
        return PVRSRV_ERROR_NOT_SUPPORTED;
 }
-#endif 
+#endif /* defined(__linux__) */
 
 PVRSRV_ERROR OSRegisterMem(IMG_CPU_PHYADDR BasePAddr,
                                                        IMG_VOID *pvCpuVAddr,
@@ -304,18 +350,33 @@ IMG_UINT32 OSGetCurrentProcessIDKM(IMG_VOID);
 IMG_UINTPTR_T OSGetCurrentThreadID( IMG_VOID );
 IMG_VOID OSMemSet(IMG_VOID *pvDest, IMG_UINT8 ui8Value, IMG_SIZE_T ui32Size);
 
-PVRSRV_ERROR OSAllocPages_Impl(IMG_UINT32 ui32Flags, IMG_SIZE_T ui32Size, IMG_UINT32 ui32PageSize, IMG_PVOID *ppvLinAddr, IMG_HANDLE *phPageAlloc);
+PVRSRV_ERROR OSAllocPages_Impl(IMG_UINT32 ui32Flags, IMG_SIZE_T ui32Size, IMG_UINT32 ui32PageSize,
+                                                          IMG_PVOID pvPrivData, IMG_UINT32 ui32PrivDataLength, IMG_HANDLE hBMHandle, IMG_PVOID *ppvLinAddr, IMG_HANDLE *phPageAlloc);
 PVRSRV_ERROR OSFreePages(IMG_UINT32 ui32Flags, IMG_SIZE_T ui32Size, IMG_PVOID pvLinAddr, IMG_HANDLE hPageAlloc);
 
 
+/*---------------------
+The set of macros below follows this pattern:
+
+f(x) = if F -> f2(g(x))
+       else -> g(x)
+
+g(x) = if G -> g2(h(x))
+       else -> h(x)
+
+h(x) = ...
+
+-----------------------*/
+
+/*If level 3 wrapper is enabled, we add a PVR_TRACE and call the next level, else just call the next level*/
 #ifdef PVRSRV_LOG_MEMORY_ALLOCS
        #define OSAllocMem(flags, size, linAddr, blockAlloc, logStr) \
                (PVR_TRACE(("OSAllocMem(" #flags ", " #size ", " #linAddr ", " #blockAlloc "): " logStr " (size = 0x%lx)", size)), \
                        OSAllocMem_Debug_Wrapper(flags, size, linAddr, blockAlloc, __FILE__, __LINE__))
 
-       #define OSAllocPages(flags, size, pageSize, linAddr, pageAlloc) \
+       #define OSAllocPages(flags, size, pageSize, privdata, privdatalength, bmhandle, linAddr, pageAlloc) \
                (PVR_TRACE(("OSAllocPages(" #flags ", " #size ", " #pageSize ", " #linAddr ", " #pageAlloc "): (size = 0x%lx)", size)), \
-                       OSAllocPages_Impl(flags, size, pageSize, linAddr, pageAlloc))
+                       OSAllocPages_Impl(flags, size, pageSize, linAddr, privdata, privdatalength, bmhandle, pageAlloc))
                
        #define OSFreeMem(flags, size, linAddr, blockAlloc) \
                (PVR_TRACE(("OSFreeMem(" #flags ", " #size ", " #linAddr ", " #blockAlloc "): (pointer = 0x%X)", linAddr)), \
@@ -330,6 +391,8 @@ PVRSRV_ERROR OSFreePages(IMG_UINT32 ui32Flags, IMG_SIZE_T ui32Size, IMG_PVOID pv
                        OSFreeMem_Debug_Wrapper(flags, size, linAddr, blockAlloc, __FILE__, __LINE__)
 #endif
  
+/*If level 2 wrapper is enabled declare the function,
+else alias to level 1 wrapper, else the wrapper function will be used*/
 #ifdef PVRSRV_DEBUG_OS_MEMORY
 
        PVRSRV_ERROR OSAllocMem_Debug_Wrapper(IMG_UINT32 ui32Flags,
@@ -360,14 +423,16 @@ PVRSRV_ERROR OSFreePages(IMG_UINT32 ui32Flags, IMG_SIZE_T ui32Size, IMG_PVOID pv
                } eValid;
        } OSMEM_DEBUG_INFO;
        
-       #define TEST_BUFFER_PADDING_STATUS (sizeof(OSMEM_DEBUG_INFO)) 
-       #define TEST_BUFFER_PADDING_AFTER  (8) 
+       #define TEST_BUFFER_PADDING_STATUS (sizeof(OSMEM_DEBUG_INFO))
+       #define TEST_BUFFER_PADDING_AFTER  (8)
        #define TEST_BUFFER_PADDING (TEST_BUFFER_PADDING_STATUS + TEST_BUFFER_PADDING_AFTER)
 #else
        #define OSAllocMem_Debug_Wrapper OSAllocMem_Debug_Linux_Memory_Allocations
        #define OSFreeMem_Debug_Wrapper OSFreeMem_Debug_Linux_Memory_Allocations
 #endif
  
+/*If level 1 wrapper is enabled declare the functions with extra parameters
+else alias to level 0 and declare the functions without the extra debugging parameters*/
 #if (defined(__linux__) || defined(__QNXNTO__)) && defined(DEBUG_LINUX_MEMORY_ALLOCATIONS)
        PVRSRV_ERROR OSAllocMem_Impl(IMG_UINT32 ui32Flags, IMG_SIZE_T ui32Size, IMG_PVOID *ppvLinAddr, IMG_HANDLE *phBlockAlloc, IMG_CHAR *pszFilename, IMG_UINT32 ui32Line);
        PVRSRV_ERROR OSFreeMem_Impl(IMG_UINT32 ui32Flags, IMG_SIZE_T ui32Size, IMG_PVOID pvLinAddr, IMG_HANDLE hBlockAlloc, IMG_CHAR *pszFilename, IMG_UINT32 ui32Line);
@@ -400,6 +465,20 @@ static INLINE IMG_CPU_PHYADDR OSMemHandleToCpuPAddr(IMG_HANDLE hOSMemHandle, IMG
        return sCpuPAddr;
 }
 #endif
+
+#if defined(__linux__)
+IMG_BOOL OSMemHandleIsPhysContig(IMG_VOID *hOSMemHandle);
+#else
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(OSMemHandleIsPhysContig)
+#endif
+static INLINE IMG_BOOL OSMemHandleIsPhysContig(IMG_HANDLE hOSMemHandle)
+{
+       PVR_UNREFERENCED_PARAMETER(hOSMemHandle);
+       return IMG_FALSE;
+}
+#endif
+
 PVRSRV_ERROR OSInitEnvData(IMG_PVOID *ppvEnvSpecificData);
 PVRSRV_ERROR OSDeInitEnvData(IMG_PVOID pvEnvSpecificData);
 IMG_CHAR* OSStringCopy(IMG_CHAR *pszDest, const IMG_CHAR *pszSrc);
@@ -426,7 +505,7 @@ PVRSRV_ERROR OSEventObjectOpenKM(PVRSRV_EVENTOBJECT *psEventObject,
                                                                                        IMG_HANDLE *phOSEvent);
 PVRSRV_ERROR OSEventObjectCloseKM(PVRSRV_EVENTOBJECT *psEventObject,
                                                                                        IMG_HANDLE hOSEventKM);
-#endif 
+#endif /* #if defined (SUPPORT_SID_INTERFACE) */
 
 
 PVRSRV_ERROR OSBaseAllocContigMemory(IMG_SIZE_T ui32Size, IMG_CPU_VIRTADDR *pLinAddr, IMG_CPU_PHYADDR *pPhysAddr);
@@ -461,15 +540,57 @@ IMG_VOID OSBreakResourceLock(PVRSRV_RESOURCE *psResource, IMG_UINT32 ui32ID);
 #define OSPowerLockWrap SysPowerLockWrap
 #define OSPowerLockUnwrap SysPowerLockUnwrap
 #else
+/******************************************************************************
+ @Function     OSPowerLockWrap
+
+ @Description  OS-specific wrapper around the power lock
+
+ @Input bTryLock - don't block on lock contention
+
+ @Return       PVRSRV_ERROR
+******************************************************************************/
 PVRSRV_ERROR OSPowerLockWrap(IMG_BOOL bTryLock);
 
+/******************************************************************************
+ @Function     OSPowerLockUnwrap
+
+ @Description  OS-specific wrapper around the power unlock
+
+ @Return       IMG_VOID
+******************************************************************************/
 IMG_VOID OSPowerLockUnwrap(IMG_VOID);
-#endif 
+#endif /* SYS_CUSTOM_POWERLOCK_WRAP */
 
+/*!
+******************************************************************************
+
+ @Function OSWaitus
+ @Description 
+    This function implements a busy wait of the specified microseconds
+    This function does NOT release thread quanta
  
+ @Input ui32Timeus - (us)
+
+ @Return IMG_VOID
+
+******************************************************************************/ 
 IMG_VOID OSWaitus(IMG_UINT32 ui32Timeus);
 
+/*!
+******************************************************************************
+
+ @Function OSSleepms
  
+ @Description 
+    This function implements a sleep of the specified milliseconds
+    This function may allow pre-emption if implemented
+ @Input ui32Timems - (ms)
+
+ @Return IMG_VOID
+
+******************************************************************************/ 
 IMG_VOID OSSleepms(IMG_UINT32 ui32Timems);
 
 IMG_HANDLE OSFuncHighResTimerCreate(IMG_VOID);
@@ -479,6 +600,14 @@ IMG_VOID OSReleaseThreadQuanta(IMG_VOID);
 IMG_UINT32 OSPCIReadDword(IMG_UINT32 ui32Bus, IMG_UINT32 ui32Dev, IMG_UINT32 ui32Func, IMG_UINT32 ui32Reg);
 IMG_VOID OSPCIWriteDword(IMG_UINT32 ui32Bus, IMG_UINT32 ui32Dev, IMG_UINT32 ui32Func, IMG_UINT32 ui32Reg, IMG_UINT32 ui32Value);
 
+IMG_IMPORT
+IMG_UINT32 ReadHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset);
+
+IMG_IMPORT
+IMG_VOID WriteHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset, IMG_UINT32 ui32Value);
+
+IMG_IMPORT IMG_VOID WriteHWRegs(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Count, PVRSRV_HWREG *psHWRegs);
+
 #ifndef OSReadHWReg
 IMG_UINT32 OSReadHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset);
 #endif
@@ -518,6 +647,17 @@ PVRSRV_ERROR OSPCIResumeDev(PVRSRV_PCI_DEV_HANDLE hPVRPCI);
 
 PVRSRV_ERROR OSScheduleMISR(IMG_VOID *pvSysData);
 
+/******************************************************************************
+
+ @Function             OSPanic
+
+ @Description  Take action in response to an unrecoverable driver error
+
+ @Input    IMG_VOID
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 IMG_VOID OSPanic(IMG_VOID);
 
 IMG_BOOL OSProcHasPrivSrvInit(IMG_VOID);
@@ -533,7 +673,7 @@ IMG_BOOL OSAccessOK(IMG_VERIFY_TEST eVerification, IMG_VOID *pvUserPtr, IMG_SIZE
 PVRSRV_ERROR OSCopyToUser(IMG_PVOID pvProcess, IMG_VOID *pvDest, IMG_VOID *pvSrc, IMG_SIZE_T ui32Bytes);
 PVRSRV_ERROR OSCopyFromUser(IMG_PVOID pvProcess, IMG_VOID *pvDest, IMG_VOID *pvSrc, IMG_SIZE_T ui32Bytes);
 
-#if (defined(__linux__) || defined(__QNXNTO__))
+#if defined(__linux__) || defined(__QNXNTO__)
 PVRSRV_ERROR OSAcquirePhysPageAddr(IMG_VOID* pvCPUVAddr, 
                                                                        IMG_SIZE_T ui32Bytes, 
                                                                        IMG_SYS_PHYADDR *psSysPAddr,
@@ -584,7 +724,7 @@ static inline IMG_VOID OSMemoryBarrier(IMG_VOID)
        mb();
 }
 
-#else 
+#else /* defined(__linux__) && defined(__KERNEL__) */
 
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(OSWriteMemoryBarrier)
@@ -596,11 +736,58 @@ static INLINE IMG_VOID OSWriteMemoryBarrier(IMG_VOID) { }
 #endif
 static INLINE IMG_VOID OSMemoryBarrier(IMG_VOID) { }
 
-#endif 
+#endif /* defined(__linux__) && defined(__KERNEL__) */
+
+/* Atomic functions */
+PVRSRV_ERROR OSAtomicAlloc(IMG_PVOID *ppvRefCount);
+IMG_VOID OSAtomicFree(IMG_PVOID pvRefCount);
+IMG_VOID OSAtomicInc(IMG_PVOID pvRefCount);
+IMG_BOOL OSAtomicDecAndTest(IMG_PVOID pvRefCount);
+IMG_UINT32 OSAtomicRead(IMG_PVOID pvRefCount);
+
+PVRSRV_ERROR OSTimeCreateWithUSOffset(IMG_PVOID *pvRet, IMG_UINT32 ui32MSOffset);
+IMG_BOOL OSTimeHasTimePassed(IMG_PVOID pvData);
+IMG_VOID OSTimeDestroy(IMG_PVOID pvData);
+
+#if defined(__linux__)
+IMG_VOID OSReleaseBridgeLock(IMG_VOID);
+IMG_VOID OSReacquireBridgeLock(IMG_VOID);
+#else
+
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(OSReleaseBridgeLock)
+#endif
+static INLINE IMG_VOID OSReleaseBridgeLock(IMG_VOID) { }
+
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(OSReacquireBridgeLock)
+#endif
+static INLINE IMG_VOID OSReacquireBridgeLock(IMG_VOID) { }
+
+#endif
+
+#if defined(__linux__)
+IMG_VOID OSGetCurrentProcessNameKM(IMG_CHAR *pszName, IMG_UINT32 ui32Size);
+#else
+
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(OSGetCurrentProcessNameKM)
+#endif
+static INLINE IMG_VOID OSGetCurrentProcessNameKM(IMG_CHAR *pszName, IMG_UINT32 ui32Size)
+{
+       PVR_UNREFERENCED_PARAMETER(pszName);
+       PVR_UNREFERENCED_PARAMETER(ui32Size);
+}
+
+#endif
 
 #if defined (__cplusplus)
 }
 #endif
 
-#endif 
+#endif /* __OSFUNC_H__ */
+
+/******************************************************************************
+ End of file (osfunc.h)
+******************************************************************************/
 
index e5c81da..0b962b4 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OS specific per process data interface
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description   OS specific per process data interface
+@License        Dual MIT/GPLv2
 
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __OSPERPROC_H__
 #define __OSPERPROC_H__
 
@@ -36,7 +51,7 @@ PVRSRV_ERROR OSPerProcessPrivateDataInit(IMG_HANDLE *phOsPrivateData);
 PVRSRV_ERROR OSPerProcessPrivateDataDeInit(IMG_HANDLE hOsPrivateData);
 
 PVRSRV_ERROR OSPerProcessSetHandleOptions(PVRSRV_HANDLE_BASE *psHandleBase);
-#else  
+#else  /* defined(__linux__) */
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(OSPerProcessPrivateDataInit)
 #endif
@@ -66,11 +81,14 @@ static INLINE PVRSRV_ERROR OSPerProcessSetHandleOptions(PVRSRV_HANDLE_BASE *psHa
 
        return PVRSRV_OK;
 }
-#endif 
+#endif /* defined(__linux__) */
 
 #if defined (__cplusplus)
 }
 #endif
 
-#endif 
+#endif /* __OSPERPROC_H__ */
 
+/******************************************************************************
+ End of file (osperproc.h)
+******************************************************************************/
index 9f68549..a76fed0 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Parameter dump internal common functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
 
 #ifndef __PDUMP_INT_H__
 #define __PDUMP_INT_H__
 extern "C" {
 #endif
 
+/*
+ *     This file contains internal pdump utility functions which may be accessed
+ *     from OS-specific code. The header should not be included outside of srvkm
+ *     pdump files.
+ */
+
 #if !defined(_UITRON)
+/*
+ *     No dbgdriver on uitron, so ignore any common functions for communicating
+ *     with dbgdriver.
+ */
 #include "dbgdrvif.h"
 
+/* Callbacks which are registered with the debug driver. */
 IMG_EXPORT IMG_VOID PDumpConnectionNotify(IMG_VOID);
 
-#endif 
+#endif /* !defined(_UITRON) */
 
 typedef enum
 {
-       
+       /* Continuous writes are always captured in the dbgdrv; the buffer will
+        * expand if no client/sink process is running.
+        */
        PDUMP_WRITE_MODE_CONTINUOUS = 0,
-       
+       /* Last frame capture */
        PDUMP_WRITE_MODE_LASTFRAME,
-       
+       /* Capture frame, binary data */
        PDUMP_WRITE_MODE_BINCM,
-       
+       /* Persistent capture, append data to init phase */
        PDUMP_WRITE_MODE_PERSISTENT
 } PDUMP_DDWMODE;
 
@@ -63,5 +92,9 @@ IMG_UINT32 PDumpOSDebugDriverWrite(   PDBG_STREAM psStream,
 #if defined (__cplusplus)
 }
 #endif
-#endif 
+#endif /* __PDUMP_INT_H__ */
+
+/******************************************************************************
+ End of file (pdump_int.h)
+******************************************************************************/
 
index 418c6d7..e4325cc 100644 (file)
@@ -1,50 +1,75 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          pdump functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Main APIs for pdump functions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef _PDUMP_KM_H_
 #define _PDUMP_KM_H_
 
 
+/*
+ * Include the OS abstraction APIs
+ */
 #include "pdump_osfunc.h"
 
 #if defined(__cplusplus)
 extern "C" {
 #endif
 
+/*
+ *     Pull in pdump flags from services include
+ */
 #include "pdump.h"
 
 #define PDUMP_PD_UNIQUETAG                     (IMG_HANDLE)0
 #define PDUMP_PT_UNIQUETAG                     (IMG_HANDLE)0
 
+/*
+ * PDump streams (common to all OSes)
+ */
 #define PDUMP_STREAM_PARAM2                    0
 #define PDUMP_STREAM_SCRIPT2           1
 #define PDUMP_STREAM_DRIVERINFO                2
 #define PDUMP_NUM_STREAMS                      3
 
 #if defined(PDUMP_DEBUG_OUTFILES)
+/* counter increments each time debug write is called */
 extern IMG_UINT32 g_ui32EveryLineCounter;
 #endif
 
@@ -114,8 +139,6 @@ extern IMG_UINT32 g_ui32EveryLineCounter;
        PVRSRV_ERROR PDumpStopInitPhaseKM(IMG_VOID);
        IMG_IMPORT PVRSRV_ERROR PDumpSetFrameKM(IMG_UINT32 ui32Frame);
        IMG_IMPORT PVRSRV_ERROR PDumpCommentKM(IMG_CHAR *pszComment, IMG_UINT32 ui32Flags);
-
-
        IMG_IMPORT PVRSRV_ERROR PDumpDriverInfoKM(IMG_CHAR *pszString, IMG_UINT32 ui32Flags);
 
        PVRSRV_ERROR PDumpRegWithFlagsKM(IMG_CHAR *pszPDumpRegName,
@@ -258,7 +281,8 @@ extern IMG_UINT32 g_ui32EveryLineCounter;
                                                        IMG_UINT32                      ui32NumBytes,
                                                        IMG_UINT32                      ui32PageSize,
                                                        IMG_HANDLE              hUniqueTag,
-                                                       IMG_BOOL                        bInterleaved);
+                                                       IMG_BOOL                        bInterleaved,
+                                                       IMG_BOOL                        bSparse);
        PVRSRV_ERROR PDumpFreePageTable(PVRSRV_DEVICE_IDENTIFIER *psDevID,
                                                                        IMG_HANDLE          hOSMemHandle,
                                                                        IMG_CPU_VIRTADDR        pvLinAddr,
@@ -309,7 +333,7 @@ extern IMG_UINT32 g_ui32EveryLineCounter;
        IMG_VOID PDumpSuspendKM(IMG_VOID);
        IMG_VOID PDumpResumeKM(IMG_VOID);
 
-       
+       /* New pdump common functions */
        PVRSRV_ERROR PDumpStoreMemToFile(PDUMP_MMU_ATTRIB *psMMUAttrib,
                                                                 IMG_CHAR *pszFileName,
                                                                         IMG_UINT32 ui32FileOffset, 
@@ -356,7 +380,7 @@ extern IMG_UINT32 g_ui32EveryLineCounter;
        #define PDUMPRESUME                             PDumpResumeKM
 
 #else
-        #if (((defined(LINUX) || defined(__QNXNTO__)) || defined(GCC_IA32)) || defined(GCC_ARM))
+#if defined LINUX || defined (__QNXNTO__) || defined GCC_IA32 || defined GCC_ARM
                        #define PDUMPMEMPOL(args...)
                        #define PDUMPMEM(args...)
                        #define PDUMPMEMPTENTRIES(args...)
@@ -410,5 +434,8 @@ extern IMG_UINT32 g_ui32EveryLineCounter;
 }
 #endif
 
-#endif 
+#endif /* _PDUMP_KM_H_ */
 
+/******************************************************************************
+ End of file (pdump_km.h)
+******************************************************************************/
index f3ed914..fb5c7c3 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          OS-independent interface to helper functions for pdump
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include <stdarg.h>
 
@@ -31,12 +46,45 @@ extern "C" {
 #endif
 
 
+/* 
+ * Some OSes (WinXP,CE) allocate the string on the stack, but some
+ * (Linux,Symbian) use a global variable/lock instead.
+ * Would be good to use the same across all OSes.
+ *
+ * A handle is returned which represents IMG_CHAR* type on all OSes except
+ * Symbian when it represents PDumpState* type.
+ *
+ * The allocated buffer length is also returned on OSes where it's
+ * supported (e.g. Linux).
+ */
 #define MAX_PDUMP_STRING_LENGTH (256)
+#if  defined(__QNXNTO__)
+#define PDUMP_GET_SCRIPT_STRING()      \
+       IMG_CHAR pszScript[MAX_PDUMP_STRING_LENGTH];            \
+       IMG_UINT32      ui32MaxLen = MAX_PDUMP_STRING_LENGTH-1; \
+       IMG_HANDLE      hScript = (IMG_HANDLE)pszScript;
+
+#define PDUMP_GET_MSG_STRING()         \
+       IMG_CHAR pszMsg[MAX_PDUMP_STRING_LENGTH];                       \
+       IMG_UINT32      ui32MaxLen = MAX_PDUMP_STRING_LENGTH-1;
 
+#define PDUMP_GET_FILE_STRING()                \
+       IMG_CHAR        pszFileName[MAX_PDUMP_STRING_LENGTH];   \
+       IMG_UINT32      ui32MaxLen = MAX_PDUMP_STRING_LENGTH-1;
+
+#define PDUMP_GET_SCRIPT_AND_FILE_STRING()             \
+       IMG_CHAR        pszScript[MAX_PDUMP_STRING_LENGTH];             \
+       IMG_CHAR        pszFileName[MAX_PDUMP_STRING_LENGTH];   \
+       IMG_UINT32      ui32MaxLenScript = MAX_PDUMP_STRING_LENGTH-1;   \
+       IMG_UINT32      ui32MaxLenFileName = MAX_PDUMP_STRING_LENGTH-1; \
+       IMG_HANDLE      hScript = (IMG_HANDLE)pszScript;
 
+#else /* WIN32 or QNX */
 
 
-       
+       /*
+        * Linux
+        */
 #define PDUMP_GET_SCRIPT_STRING()                              \
        IMG_HANDLE hScript;                                                     \
        IMG_UINT32      ui32MaxLen;                                             \
@@ -69,17 +117,43 @@ extern "C" {
        eError = PDumpOSGetFilenameString(&pszFileName, &ui32MaxLenFileName);\
        if(eError != PVRSRV_OK) return eError;
 
-       
+       /*!
+        * @name        PDumpOSGetScriptString
+        * @brief       Get the "script" buffer
+        * @param       phScript - buffer handle for pdump script
+        * @param       pui32MaxLen - max length of the script buffer
+        *              FIXME: the max length should be internal to the OS-specific code
+        * @return      error (always PVRSRV_OK on some OSes)
+        */
        PVRSRV_ERROR PDumpOSGetScriptString(IMG_HANDLE *phScript, IMG_UINT32 *pui32MaxLen);
 
-       
+       /*!
+        * @name        PDumpOSGetMessageString
+        * @brief       Get the "message" buffer
+        * @param       pszMsg - buffer pointer for pdump messages
+        * @param       pui32MaxLen - max length of the message buffer
+        *              FIXME: the max length should be internal to the OS-specific code
+        * @return      error (always PVRSRV_OK on some OSes)
+        */
        PVRSRV_ERROR PDumpOSGetMessageString(IMG_CHAR **ppszMsg, IMG_UINT32 *pui32MaxLen);
 
-       
+       /*!
+        * @name        PDumpOSGetFilenameString
+        * @brief       Get the "filename" buffer
+        * @param       ppszFile - buffer pointer for filename
+        * @param       pui32MaxLen - max length of the filename buffer
+        *              FIXME: the max length should be internal to the OS-specific code
+        * @return      error (always PVRSRV_OK on some OSes)
+        */
        PVRSRV_ERROR PDumpOSGetFilenameString(IMG_CHAR **ppszFile, IMG_UINT32 *pui32MaxLen);
 
+#endif /* WIN32 or QNX */
 
 
+/*
+ * Define macro for processing variable args list in OS-independent
+ * manner. See e.g. PDumpComment().
+ */
 
 #define PDUMP_va_list  va_list
 #define PDUMP_va_start va_start
@@ -87,37 +161,138 @@ extern "C" {
 
 
 
+/*!
+ * @name       PDumpOSGetStream
+ * @brief      Get a handle to the labelled stream (cast the handle to PDBG_STREAM to use it)
+ * @param      ePDumpStream - stream label
+ */
 IMG_HANDLE PDumpOSGetStream(IMG_UINT32 ePDumpStream);
 
+/*!
+ * @name       PDumpOSGetStreamOffset
+ * @brief      Return current offset within the labelled stream
+ * @param      ePDumpStream - stream label
+ */
 IMG_UINT32 PDumpOSGetStreamOffset(IMG_UINT32 ePDumpStream);
 
+/*!
+ * @name       PDumpOSGetParamFileNum
+ * @brief      Return file number of the 'script' stream, in the case that the file was split
+ * @param      ePDumpStream - stream label
+ */
 IMG_UINT32 PDumpOSGetParamFileNum(IMG_VOID);
 
+/*!
+ * @name       PDumpOSCheckForSplitting
+ * @brief      Check if the requested pdump params are too large for a single file
+ * @param      hStream - pdump stream
+ * @param      ui32Size - size of params to dump (bytes)
+ * @param      ui32Flags - pdump flags
+ */
 IMG_VOID PDumpOSCheckForSplitting(IMG_HANDLE hStream, IMG_UINT32 ui32Size, IMG_UINT32 ui32Flags);
 
+/*!
+ * @name       PDumpOSIsSuspended
+ * @brief      Is the pdump stream busy?
+ * @return     IMG_BOOL
+ */
 IMG_BOOL PDumpOSIsSuspended(IMG_VOID);
 
+/*!
+ * @name       PDumpOSIsSuspended
+ * @brief      Is the pdump jump table initialised?
+ * @return     IMG_BOOL
+ */
 IMG_BOOL PDumpOSJTInitialised(IMG_VOID);
 
+/*!
+ * @name       PDumpOSWriteString
+ * @brief      General function for writing to pdump stream.
+ *                     Usually more convenient to use PDumpOSWriteString2 below.
+ * @param      hDbgStream - pdump stream handle
+ * @param      psui8Data - data to write
+ * @param      ui32Size - size of write
+ * @param      ui32Flags - pdump flags
+ * @return     error
+ */
 IMG_BOOL PDumpOSWriteString(IMG_HANDLE hDbgStream,
                IMG_UINT8 *psui8Data,
                IMG_UINT32 ui32Size,
                IMG_UINT32 ui32Flags);
 
+/*!
+ * @name       PDumpOSWriteString2
+ * @brief      Write a string to the "script" output stream
+ * @param      pszScript - buffer to write (ptr to state structure on Symbian)
+ * @param      ui32Flags - pdump flags
+ * @return     error
+ */
 IMG_BOOL PDumpOSWriteString2(IMG_HANDLE        hScript, IMG_UINT32 ui32Flags);
 
+/*!
+ * @name       PDumpOSBufprintf
+ * @brief      Printf to OS-specific pdump state buffer
+ * @param      hBuf - buffer handle to write into (ptr to state structure on Symbian)
+ * @param      ui32ScriptSizeMax - maximum size of data to write (not supported on all OSes)
+ * @param      pszFormat - format string
+ */
 PVRSRV_ERROR PDumpOSBufprintf(IMG_HANDLE hBuf, IMG_UINT32 ui32ScriptSizeMax, IMG_CHAR* pszFormat, ...) IMG_FORMAT_PRINTF(3, 4);
 
+/*!
+ * @name       PDumpOSDebugPrintf
+ * @brief      Debug message during pdumping
+ * @param      pszFormat - format string
+ */
 IMG_VOID PDumpOSDebugPrintf(IMG_CHAR* pszFormat, ...) IMG_FORMAT_PRINTF(1, 2);
 
+/*
+ * FIXME: Is this function useful for Symbian?
+ * Write into a IMG_CHAR* on all OSes. Can be allocated on the stack or heap.
+ */
+/*!
+ * @name       PDumpOSSprintf
+ * @brief      Printf to IMG char array
+ * @param      pszComment - char array to print into
+ * @param      pszFormat - format string
+ */
 PVRSRV_ERROR PDumpOSSprintf(IMG_CHAR *pszComment, IMG_UINT32 ui32ScriptSizeMax, IMG_CHAR *pszFormat, ...) IMG_FORMAT_PRINTF(3, 4);
 
+/*!
+ * @name       PDumpOSVSprintf
+ * @brief      Printf to IMG string using variable args (see stdarg.h). This is necessary
+ *                     because the ... notation does not support nested function calls.
+ * @param      pszMsg - char array to print into
+ * @param      ui32ScriptSizeMax - maximum size of data to write (not supported on all OSes)
+ * @param      pszFormat - format string
+ * @param      vaArgs - variable args structure (from stdarg.h)
+ */
 PVRSRV_ERROR PDumpOSVSprintf(IMG_CHAR *pszMsg, IMG_UINT32 ui32ScriptSizeMax, IMG_CHAR* pszFormat, PDUMP_va_list vaArgs) IMG_FORMAT_PRINTF(3, 0);
 
+/*!
+ * @name       PDumpOSBuflen
+ * @param      hBuffer - handle to buffer (ptr to state structure on Symbian)
+ * @param      ui32BuffeRSizeMax - max size of buffer (chars)
+ * @return     length of buffer, will always be <= ui32BufferSizeMax
+ */
 IMG_UINT32 PDumpOSBuflen(IMG_HANDLE hBuffer, IMG_UINT32 ui32BufferSizeMax);
 
+/*!
+ * @name       PDumpOSVerifyLineEnding
+ * @brief      Put \r\n sequence at the end if it isn't already there
+ * @param      hBuffer - handle to buffer
+ * @param      ui32BufferSizeMax - max size of buffer (chars)
+ */
 IMG_VOID PDumpOSVerifyLineEnding(IMG_HANDLE hBuffer, IMG_UINT32 ui32BufferSizeMax);
 
+/*!
+ * @name       PDumpOSCPUVAddrToDevPAddr
+ * @brief      OS function to convert CPU virtual to device physical for dumping pages
+ * @param      hOSMemHandle    mem allocation handle (used if kernel virtual mem space is limited, e.g. linux)
+ * @param      ui32Offset              dword offset into allocation (for use with mem handle, e.g. linux)
+ * @param      pui8LinAddr             CPU linear addr (usually a kernel virtual address)
+ * @param      ui32PageSize    page size, used for assertion check
+ * @return     psDevPAddr              device physical addr
+ */
 IMG_VOID PDumpOSCPUVAddrToDevPAddr(PVRSRV_DEVICE_TYPE eDeviceType,
         IMG_HANDLE hOSMemHandle,
                IMG_UINT32 ui32Offset,
@@ -125,16 +300,37 @@ IMG_VOID PDumpOSCPUVAddrToDevPAddr(PVRSRV_DEVICE_TYPE eDeviceType,
                IMG_UINT32 ui32PageSize,
                IMG_DEV_PHYADDR *psDevPAddr);
 
+/*!
+ * @name       PDumpOSCPUVAddrToPhysPages
+ * @brief      OS function to convert CPU virtual to backing physical pages
+ * @param      hOSMemHandle    mem allocation handle (used if kernel virtual mem space is limited, e.g. linux)
+ * @param      ui32Offset              offset within mem allocation block
+ * @param      pui8LinAddr             CPU linear addr
+ * @param      ui32DataPageMask        mask for data page (= data page size -1)
+ * @return     pui32PageOffset CPU page offset (same as device page offset if page sizes equal)
+ */
 IMG_VOID PDumpOSCPUVAddrToPhysPages(IMG_HANDLE hOSMemHandle,
                IMG_UINT32 ui32Offset,
                IMG_PUINT8 pui8LinAddr,
                IMG_UINT32 ui32DataPageMask,
                IMG_UINT32 *pui32PageOffset);
 
+/*!
+ * @name       PDumpOSReleaseExecution
+ * @brief      OS function to switch to another process, to clear pdump buffers
+ */
 IMG_VOID PDumpOSReleaseExecution(IMG_VOID);
 
+/*!
+ * @name       PDumpOSIsCaptureFrameKM
+ * @brief      Is the current frame a capture frame?
+ */
 IMG_BOOL PDumpOSIsCaptureFrameKM(IMG_VOID);
 
+/*!
+ * @name       PDumpOSSetFrameKM
+ * @brief      Set frame counter
+ */
 PVRSRV_ERROR PDumpOSSetFrameKM(IMG_UINT32 ui32Frame);
 
 #if defined (__cplusplus)
diff --git a/services4/srvkm/include/perfkm.h b/services4/srvkm/include/perfkm.h
new file mode 100644 (file)
index 0000000..715c2c4
--- /dev/null
@@ -0,0 +1,58 @@
+/*************************************************************************/ /*!
+@Title          Vista-specific Perf initialisation
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+#ifndef _PERFKM_H_
+#define _PERFKM_H_
+
+#include "img_types.h"
+
+/*
+ * Note, WDDM needs to perform initialisation and deinitialisation
+ * in order to support HW performance measurement.  Other platforms
+ * should not need to do anything in these functions.
+ */
+#define PERFINIT()
+#define PERFDEINIT()
+
+#endif /* _PERFKM_H_ */
+
+/******************************************************************************
+  End of file (perfkm.h)
+******************************************************************************/
index 842680c..d603613 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Handle Manager API
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description   Perprocess data
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef __PERPROC_H__
 #define __PERPROC_H__
 
@@ -48,27 +63,33 @@ typedef struct _PVRSRV_PER_PROCESS_DATA_
 #endif
        PVRSRV_HANDLE_BASE      *psHandleBase;
 #if defined (SUPPORT_SID_INTERFACE)
-       
+       /* Handles are being allocated in batches */
        IMG_BOOL                bHandlesBatched;
 #else
 #if defined (PVR_SECURE_HANDLES)
-       
+       /* Handles are being allocated in batches */
        IMG_BOOL                bHandlesBatched;
-#endif  
-#endif 
+#endif  /* PVR_SECURE_HANDLES */
+#endif /* SUPPORT_SID_INTERFACE */
        IMG_UINT32              ui32RefCount;
 
-       
+       /* True if the process is the initialisation server. */
        IMG_BOOL                bInitProcess;
 #if defined(PDUMP)
-       
+       /* True if pdump data from the process is 'persistent' */
        IMG_BOOL                bPDumpPersistent;
 #if defined(SUPPORT_PDUMP_MULTI_PROCESS)
-       
+       /* True if this process is marked for pdumping. This flag is
+        * significant in a multi-app environment.
+        */
        IMG_BOOL                bPDumpActive;
-#endif 
+#endif /* SUPPORT_PDUMP_MULTI_PROCESS */
 #endif
-       
+       /*
+        * OS specific data can be stored via this handle.
+        * See osperproc.h for a generic mechanism for initialising
+        * this field.
+        */
        IMG_HANDLE              hOsPrivateData;
 } PVRSRV_PER_PROCESS_DATA;
 
@@ -122,5 +143,8 @@ IMG_HANDLE PVRSRVFindPerProcessPrivateData(IMG_VOID)
 }
 #endif
 
-#endif 
+#endif /* __PERPROC_H__ */
 
+/******************************************************************************
+ End of file (perproc.h)
+******************************************************************************/
index 9e3dcc4..0abaf75 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Power Management Functions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Main APIs for power management functions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #ifndef POWER_H
 #define POWER_H
 
@@ -32,6 +47,10 @@ extern "C" {
 #endif
 
 
+/*!
+ *****************************************************************************
+ *     Power management
+ *****************************************************************************/
  
 typedef struct _PVRSRV_POWER_DEV_TAG_
 {
@@ -75,9 +94,7 @@ IMG_VOID PVRSRVPowerUnlock(IMG_UINT32 ui32CallerID);
 
 IMG_IMPORT
 PVRSRV_ERROR PVRSRVSetDevicePowerStateKM(IMG_UINT32                            ui32DeviceIndex,
-                                                                                PVRSRV_DEV_POWER_STATE eNewPowerState,
-                                                                                IMG_UINT32                             ui32CallerID,
-                                                                                IMG_BOOL                               bRetainMutex);
+                                                                                PVRSRV_DEV_POWER_STATE eNewPowerState);
 
 IMG_IMPORT
 PVRSRV_ERROR PVRSRVSystemPrePowerStateKM(PVRSRV_SYS_POWER_STATE eNewPowerState);
@@ -116,5 +133,8 @@ IMG_VOID PVRSRVDevicePostClockSpeedChange(IMG_UINT32        ui32DeviceIndex,
 #if defined (__cplusplus)
 }
 #endif
-#endif 
+#endif /* POWER_H */
 
+/******************************************************************************
+ End of file (power.h)
+******************************************************************************/
index ab89527..58f8093 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Command Queue API
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Internal structures and definitions for command queues
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef QUEUE_H
 #define QUEUE_H
 extern "C" {
 #endif
 
+/*!
+ * Macro to Read Offset in given command queue
+ */
 #define UPDATE_QUEUE_ROFF(psQueue, ui32Size)                                           \
        (psQueue)->ui32ReadOffset = ((psQueue)->ui32ReadOffset + (ui32Size))    \
        & ((psQueue)->ui32QueueSize - 1);
 
+/*!
+       generic cmd complete structure.
+       This structure represents the storage required between starting and finishing
+       a given cmd and is required to hold the generic sync object update data.
+       note: for any given system we know what command types we support and
+       therefore how much storage is required for any number of commands in progress
+ */
  typedef struct _COMMAND_COMPLETE_DATA_
  {
        IMG_BOOL                        bInUse;
-               
-       IMG_UINT32                      ui32DstSyncCount;       
-       IMG_UINT32                      ui32SrcSyncCount;       
-       PVRSRV_SYNC_OBJECT      *psDstSync;                     
-       PVRSRV_SYNC_OBJECT      *psSrcSync;                     
-       IMG_UINT32                      ui32AllocSize;          
+       /* <arg(s) to PVRSRVProcessQueues>;     */      /*!< TBD */
+       IMG_UINT32                      ui32DstSyncCount;       /*!< number of dst sync objects */
+       IMG_UINT32                      ui32SrcSyncCount;       /*!< number of src sync objects */
+       PVRSRV_SYNC_OBJECT      *psDstSync;                     /*!< dst sync ptr list, 
+                                               allocated on back of this structure */
+       PVRSRV_SYNC_OBJECT      *psSrcSync;                     /*!< src sync ptr list, 
+                                                       allocated on back of this structure */
+       IMG_UINT32                      ui32AllocSize;          /*!< allocated size*/
+       PFN_QUEUE_COMMAND_COMPLETE      pfnCommandComplete;     /*!< Command complete callback */
+       IMG_HANDLE                                      hCallbackData;          /*!< Command complete callback data */
  }COMMAND_COMPLETE_DATA, *PCOMMAND_COMPLETE_DATA;
 
 #if !defined(USE_CODE)
@@ -76,7 +106,9 @@ PVRSRV_ERROR IMG_CALLCONV PVRSRVInsertCommandKM(PVRSRV_QUEUE_INFO    *psQueue,
                                                                                                PVRSRV_KERNEL_SYNC_INFO *apsDstSync[],
                                                                                                IMG_UINT32                      ui32SrcSyncCount,
                                                                                                PVRSRV_KERNEL_SYNC_INFO *apsSrcSync[],
-                                                                                               IMG_SIZE_T                      ui32DataByteSize );
+                                                                                               IMG_SIZE_T                      ui32DataByteSize,
+                                                                                               PFN_QUEUE_COMMAND_COMPLETE pfnCommandComplete,
+                                                                                               IMG_HANDLE                      hCallbackData);
 
 IMG_IMPORT
 PVRSRV_ERROR IMG_CALLCONV PVRSRVGetQueueSpaceKM(PVRSRV_QUEUE_INFO *psQueue,
@@ -99,12 +131,15 @@ IMG_IMPORT
 PVRSRV_ERROR PVRSRVRemoveCmdProcListKM(IMG_UINT32      ui32DevIndex,
                                                                           IMG_UINT32   ui32CmdCount);
 
-#endif 
+#endif /* !defined(USE_CODE) */
 
 
 #if defined (__cplusplus)
 }
 #endif
 
-#endif 
+#endif /* QUEUE_H */
 
+/******************************************************************************
+ End of file (queue.h)
+******************************************************************************/
index db141f6..aaeb345 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Resource Allocator API
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _RA_H_
 #define _RA_H_
 #include "hash.h"
 #include "osfunc.h"
 
-typedef struct _RA_ARENA_ RA_ARENA;                    
+/** Resource arena.
+ *  struct _RA_ARENA_ deliberately opaque
+ */
+typedef struct _RA_ARENA_ RA_ARENA;                    //PRQA S 3313
 typedef struct _BM_MAPPING_ BM_MAPPING;
 
 
 
+/** Enable support for arena statistics. */
 #define RA_STATS 
 
 
+/** Resource arena statistics. */
 struct _RA_STATISTICS_
 {
-    
+    /** total number of segments add to the arena */
     IMG_SIZE_T uSpanCount;
 
-    
+    /** number of current live segments within the arena */
     IMG_SIZE_T uLiveSegmentCount;
 
-    
+    /** number of current free segments within the arena */
     IMG_SIZE_T uFreeSegmentCount;
 
-    
+    /** total number of resource within the arena */
     IMG_SIZE_T uTotalResourceCount;
     
-    
+    /** number of free resource within the arena */
     IMG_SIZE_T uFreeResourceCount;
 
-    
+    /** total number of resources allocated from the arena */
     IMG_SIZE_T uCumulativeAllocs;
 
-    
+    /** total number of resources returned to the arena */
     IMG_SIZE_T uCumulativeFrees;
 
-    
+    /** total number of spans allocated by the callback mechanism */
     IMG_SIZE_T uImportCount;
 
-    
+    /** total number of spans deallocated by the callback mechanism */
     IMG_SIZE_T uExportCount;
 };
 typedef struct _RA_STATISTICS_ RA_STATISTICS;
@@ -78,6 +98,23 @@ struct _RA_SEGMENT_DETAILS_
 };
 typedef struct _RA_SEGMENT_DETAILS_ RA_SEGMENT_DETAILS;
 
+/**
+ *  @Function   RA_Create
+ *
+ *  @Description
+ *
+ *  To create a resource arena.
+ *
+ *  @Input name - the name of the arena for diagnostic purposes.
+ *  @Input base - the base of an initial resource span or 0.
+ *  @Input uSize - the size of an initial resource span or 0.
+ *  @Input pRef - the reference to return for the initial resource or 0.
+ *  @Input uQuantum - the arena allocation quantum.
+ *  @Input alloc - a resource allocation callback or 0.
+ *  @Input free - a resource de-allocation callback or 0.
+ *  @Input import_handle - handle passed to alloc and free or 0.
+ *  @Return arena handle, or IMG_NULL.
+ */
 RA_ARENA *
 RA_Create (IMG_CHAR *name,
            IMG_UINTPTR_T base,
@@ -89,6 +126,8 @@ RA_Create (IMG_CHAR *name,
                                 IMG_SIZE_T *pActualSize,
                                 BM_MAPPING **ppsMapping,
                                 IMG_UINT32 uFlags,
+                                                               IMG_PVOID pvPrivData,
+                                                               IMG_UINT32 ui32PrivDataLength,
                                 IMG_UINTPTR_T *pBase),
            IMG_VOID (*imp_free) (IMG_VOID *,
                                 IMG_UINTPTR_T,
@@ -99,15 +138,73 @@ RA_Create (IMG_CHAR *name,
                                           IMG_HANDLE),
            IMG_VOID *import_handle);
 
+/**
+ *  @Function   RA_Delete
+ *
+ *  @Description
+ *
+ *  To delete a resource arena. All resources allocated from the arena
+ *  must be freed before deleting the arena.
+ *                  
+ *  @Input  pArena - the arena to delete.
+ *  @Return None
+ */
 IMG_VOID
 RA_Delete (RA_ARENA *pArena);
 
+/**
+ *  @Function   RA_TestDelete
+ *
+ *  @Description
+ *
+ *  To test whether it is safe to delete a resource arena. If any allocations
+ *     have not been freed, the RA must not be deleted.
+ *                  
+ *  @Input  pArena - the arena to test.
+ *  @Return IMG_BOOL - IMG_TRUE if is safe to go on and call RA_Delete.
+ */
 IMG_BOOL
 RA_TestDelete (RA_ARENA *pArena);
 
+/**
+ *  @Function   RA_Add
+ *
+ *  @Description
+ *
+ *  To add a resource span to an arena. The span must not overlap with
+ *  any span previously added to the arena.
+ *
+ *  @Input pArena - the arena to add a span into.
+ *  @Input base - the base of the span.
+ *  @Input uSize - the extent of the span.
+ *  @Return IMG_TRUE - success, IMG_FALSE - failure
+ */
 IMG_BOOL
 RA_Add (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_SIZE_T uSize);
 
+/**
+ *  @Function   RA_Alloc
+ *
+ *  @Description
+ *
+ *  To allocate resource from an arena.
+ *
+ *  @Input  pArena - the arena
+ *  @Input  uRequestSize - the size of resource segment requested.
+ *  @Output pActualSize - the actual_size of resource segment allocated,
+ *          typcially rounded up by quantum.
+ *  @Output ppsMapping - the user reference associated with allocated
+ *          resource span.
+ *  @Input  uFlags - flags influencing allocation policy.
+ *  @Input  uAlignment - the alignment constraint required for the
+ *          allocated segment, use 0 if alignment not required.
+ *     @Input  uAlignmentOffset - the required alignment offset
+ *  @Input  pvPrivData - private data passed to OS allocator
+ *  @Input  ui32PrivData - length of private data
+ *
+ *  @Output pBase - allocated base resource
+ *  @Return IMG_TRUE - success, IMG_FALSE - failure
+ */
 IMG_BOOL
 RA_Alloc (RA_ARENA *pArena, 
           IMG_SIZE_T uSize,
@@ -116,8 +213,21 @@ RA_Alloc (RA_ARENA *pArena,
           IMG_UINT32 uFlags,
           IMG_UINT32 uAlignment,
                  IMG_UINT32 uAlignmentOffset,
+                 IMG_PVOID pvPrivData,
+                 IMG_UINT32 ui32PrivDataLength,
           IMG_UINTPTR_T *pBase);
 
+/**
+ *  @Function   RA_Free
+ *
+ *  @Description    To free a resource segment.
+ *  
+ *  @Input  pArena - the arena the segment was originally allocated from.
+ *  @Input  base - the base of the resource span to free.
+ *     @Input  bFreeBackingStore - Should backing store memory be freed?
+ *
+ *  @Return None
+ */
 IMG_VOID 
 RA_Free (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_BOOL bFreeBackingStore);
 
@@ -142,9 +252,30 @@ RA_Free (RA_ARENA *pArena, IMG_UINTPTR_T base, IMG_BOOL bFreeBackingStore);
 }
 
 
+/**
+ * @Function    RA_GetNextLiveSegment
+ * 
+ * @Description Returns details of the next live resource segments
+ * 
+ * @Input       pArena - the arena the segment was originally allocated from.
+ * @Output      psSegDetails - rtn details of segments
+ * 
+ * @Return      IMG_TRUE if operation succeeded
+ */
 IMG_BOOL RA_GetNextLiveSegment(IMG_HANDLE hArena, RA_SEGMENT_DETAILS *psSegDetails);
 
 
+/**
+ *  @Function   RA_GetStats
+ *
+ *  @Description    gets stats on a given arena
+ *  
+ *  @Input  pArena - the arena the segment was originally allocated from.
+ *  @Input  ppszStr - string to write stats to 
+ *     @Input  pui32StrLen - length of string
+ *
+ *  @Return PVRSRV_ERROR
+ */
 PVRSRV_ERROR RA_GetStats(RA_ARENA *pArena,
                                                        IMG_CHAR **ppszStr, 
                                                        IMG_UINT32 *pui32StrLen);
@@ -153,7 +284,7 @@ PVRSRV_ERROR RA_GetStatsFreeMem(RA_ARENA *pArena,
                                                                IMG_CHAR **ppszStr, 
                                                                IMG_UINT32 *pui32StrLen);
 
-#endif 
+#endif /* #ifdef RA_STATS */
 
 #endif
 
diff --git a/services4/srvkm/include/refcount.h b/services4/srvkm/include/refcount.h
new file mode 100644 (file)
index 0000000..0e3479d
--- /dev/null
@@ -0,0 +1,203 @@
+/*************************************************************************/ /*!
+@Title          Services reference count debugging
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+#ifndef __REFCOUNT_H__
+#define __REFCOUNT_H__
+
+#include "pvr_bridge_km.h"
+
+#if defined(PVRSRV_REFCOUNT_DEBUG)
+
+void PVRSRVDumpRefCountCCB(void);
+
+#define PVRSRVKernelSyncInfoIncRef(x...) \
+       PVRSRVKernelSyncInfoIncRef2(__FILE__, __LINE__, x)
+#define PVRSRVKernelSyncInfoDecRef(x...) \
+       PVRSRVKernelSyncInfoDecRef2(__FILE__, __LINE__, x)
+#define PVRSRVKernelMemInfoIncRef(x...) \
+       PVRSRVKernelMemInfoIncRef2(__FILE__, __LINE__, x)
+#define PVRSRVKernelMemInfoDecRef(x...) \
+       PVRSRVKernelMemInfoDecRef2(__FILE__, __LINE__, x)
+#define PVRSRVBMBufIncRef(x...) \
+       PVRSRVBMBufIncRef2(__FILE__, __LINE__, x)
+#define PVRSRVBMBufDecRef(x...) \
+       PVRSRVBMBufDecRef2(__FILE__, __LINE__, x)
+#define PVRSRVBMBufIncExport(x...) \
+       PVRSRVBMBufIncExport2(__FILE__, __LINE__, x)
+#define PVRSRVBMBufDecExport(x...) \
+       PVRSRVBMBufDecExport2(__FILE__, __LINE__, x)
+
+void PVRSRVKernelSyncInfoIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                                PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo,
+                                                                PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo);
+void PVRSRVKernelSyncInfoDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                                PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo,
+                                                                PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo);
+void PVRSRVKernelMemInfoIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo);
+void PVRSRVKernelMemInfoDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo);
+void PVRSRVBMBufIncRef2(const IMG_CHAR *pszFile,
+                                               IMG_INT iLine, BM_BUF *pBuf);
+void PVRSRVBMBufDecRef2(const IMG_CHAR *pszFile,
+                                               IMG_INT iLine, BM_BUF *pBuf);
+void PVRSRVBMBufIncExport2(const IMG_CHAR *pszFile,
+                                                  IMG_INT iLine, BM_BUF *pBuf);
+void PVRSRVBMBufDecExport2(const IMG_CHAR *pszFile,
+                                                  IMG_INT iLine, BM_BUF *pBuf);
+void PVRSRVBMXProcIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                 IMG_UINT32 ui32Index);
+void PVRSRVBMXProcDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                 IMG_UINT32 ui32Index);
+
+#if defined(__linux__)
+
+/* mmap refcounting is Linux specific */
+#include "mmap.h"
+
+#define PVRSRVOffsetStructIncRef(x...) \
+       PVRSRVOffsetStructIncRef2(__FILE__, __LINE__, x)
+#define PVRSRVOffsetStructDecRef(x...) \
+       PVRSRVOffsetStructDecRef2(__FILE__, __LINE__, x)
+#define PVRSRVOffsetStructIncMapped(x...) \
+       PVRSRVOffsetStructIncMapped2(__FILE__, __LINE__, x)
+#define PVRSRVOffsetStructDecMapped(x...) \
+       PVRSRVOffsetStructDecMapped2(__FILE__, __LINE__, x)
+
+void PVRSRVOffsetStructIncRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                          PKV_OFFSET_STRUCT psOffsetStruct);
+void PVRSRVOffsetStructDecRef2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                          PKV_OFFSET_STRUCT psOffsetStruct);
+void PVRSRVOffsetStructIncMapped2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                                 PKV_OFFSET_STRUCT psOffsetStruct);
+void PVRSRVOffsetStructDecMapped2(const IMG_CHAR *pszFile, IMG_INT iLine,
+                                                                 PKV_OFFSET_STRUCT psOffsetStruct);
+
+#endif /* defined(__linux__) */
+
+#else /* defined(PVRSRV_REFCOUNT_DEBUG) */
+
+static INLINE void PVRSRVDumpRefCountCCB(void) { }
+
+static INLINE void PVRSRVKernelSyncInfoIncRef(PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo,
+                                                               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       PVR_UNREFERENCED_PARAMETER(psKernelMemInfo);
+       PVRSRVAcquireSyncInfoKM(psKernelSyncInfo);
+}
+
+static INLINE void PVRSRVKernelSyncInfoDecRef(PVRSRV_KERNEL_SYNC_INFO *psKernelSyncInfo,
+                                                               PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       PVR_UNREFERENCED_PARAMETER(psKernelMemInfo);
+       PVRSRVReleaseSyncInfoKM(psKernelSyncInfo);
+}
+
+static INLINE void PVRSRVKernelMemInfoIncRef(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       psKernelMemInfo->ui32RefCount++;
+}
+
+static INLINE void PVRSRVKernelMemInfoDecRef(PVRSRV_KERNEL_MEM_INFO *psKernelMemInfo)
+{
+       psKernelMemInfo->ui32RefCount--;
+}
+
+static INLINE void PVRSRVBMBufIncRef(BM_BUF *pBuf)
+{
+       pBuf->ui32RefCount++;
+}
+
+static INLINE void PVRSRVBMBufDecRef(BM_BUF *pBuf)
+{
+       pBuf->ui32RefCount--;
+}
+
+static INLINE void PVRSRVBMBufIncExport(BM_BUF *pBuf)
+{
+       pBuf->ui32ExportCount++;
+}
+
+static INLINE void PVRSRVBMBufDecExport(BM_BUF *pBuf)
+{
+       pBuf->ui32ExportCount--;
+}
+
+static INLINE void PVRSRVBMXProcIncRef(IMG_UINT32 ui32Index)
+{
+       gXProcWorkaroundShareData[ui32Index].ui32RefCount++;
+}
+
+static INLINE void PVRSRVBMXProcDecRef(IMG_UINT32 ui32Index)
+{
+       gXProcWorkaroundShareData[ui32Index].ui32RefCount--;
+}
+
+#if defined(__linux__)
+
+/* mmap refcounting is Linux specific */
+#include "mmap.h"
+
+static INLINE void PVRSRVOffsetStructIncRef(PKV_OFFSET_STRUCT psOffsetStruct)
+{
+       psOffsetStruct->ui32RefCount++;
+}
+
+static INLINE void PVRSRVOffsetStructDecRef(PKV_OFFSET_STRUCT psOffsetStruct)
+{
+       psOffsetStruct->ui32RefCount--;
+}
+
+static INLINE void PVRSRVOffsetStructIncMapped(PKV_OFFSET_STRUCT psOffsetStruct)
+{
+       psOffsetStruct->ui32Mapped++;
+}
+
+static INLINE void PVRSRVOffsetStructDecMapped(PKV_OFFSET_STRUCT psOffsetStruct)
+{
+       psOffsetStruct->ui32Mapped--;
+}
+
+#endif /* defined(__linux__) */
+
+#endif /* defined(PVRSRV_REFCOUNT_DEBUG) */
+
+#endif /* __REFCOUNT_H__ */
index 648e490..92659d9 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Resource Manager API
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description   Provide resource management
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __RESMAN_H__
 #define __RESMAN_H__
 extern "C" {
 #endif
 
-enum {
-       
-       RESMAN_TYPE_SHARED_PB_DESC = 1,                                 
-       RESMAN_TYPE_SHARED_PB_DESC_CREATE_LOCK,                         
-       RESMAN_TYPE_HW_RENDER_CONTEXT,                                  
-       RESMAN_TYPE_HW_TRANSFER_CONTEXT,                                
-       RESMAN_TYPE_HW_2D_CONTEXT,                                              
-       RESMAN_TYPE_TRANSFER_CONTEXT,                                   
-
-       
-       RESMAN_TYPE_DMA_CLIENT_FIFO_DATA,                               
-
-       
-       
-       
-       
-       RESMAN_TYPE_DISPLAYCLASS_SWAPCHAIN_REF,                 
-       RESMAN_TYPE_DISPLAYCLASS_DEVICE,                                
+/******************************************************************************
+ * resman definitions 
+ *****************************************************************************/
 
+enum {
+       /* SGX: */
+       RESMAN_TYPE_SHARED_PB_DESC = 1,                                 /*!< Parameter buffer kernel stubs */
+       RESMAN_TYPE_SHARED_PB_DESC_CREATE_LOCK,                         /*!< Shared parameter buffer creation lock */
+       RESMAN_TYPE_HW_RENDER_CONTEXT,                                  /*!< Hardware Render Context Resource */
+       RESMAN_TYPE_HW_TRANSFER_CONTEXT,                                /*!< Hardware transfer Context Resource */
+       RESMAN_TYPE_HW_2D_CONTEXT,                                              /*!< Hardware 2D Context Resource */
+       RESMAN_TYPE_TRANSFER_CONTEXT,                                   /*!< Transfer Queue context */
+
+       /* VGX: */
+       RESMAN_TYPE_DMA_CLIENT_FIFO_DATA,                               /*!< VGX DMA Client FIFO data */
+
+       /* DISPLAY CLASS: */
+       RESMAN_TYPE_DISPLAYCLASS_SWAPCHAIN_REF,                 /*!< Display Class Swapchain Reference Resource */
+       RESMAN_TYPE_DISPLAYCLASS_DEVICE,                                /*!< Display Class Device Resource */
+
+       /* BUFFER CLASS: */
+       RESMAN_TYPE_BUFFERCLASS_DEVICE,                                 /*!< Buffer Class Device Resource */
        
-       RESMAN_TYPE_BUFFERCLASS_DEVICE,                                 
-       
-       
-       RESMAN_TYPE_OS_USERMODE_MAPPING,                                
-       
-       
-       RESMAN_TYPE_DEVICEMEM_CONTEXT,                                  
-       RESMAN_TYPE_DEVICECLASSMEM_MAPPING,                             
-       RESMAN_TYPE_DEVICEMEM_MAPPING,                                  
-       RESMAN_TYPE_DEVICEMEM_WRAP,                                             
-       RESMAN_TYPE_DEVICEMEM_ALLOCATION,                               
-       RESMAN_TYPE_EVENT_OBJECT,                                               
-    RESMAN_TYPE_SHARED_MEM_INFO,                    
-    RESMAN_TYPE_MODIFY_SYNC_OPS,                                       
-    RESMAN_TYPE_SYNC_INFO,                                             
+       /* OS specific User mode Mappings: */
+       RESMAN_TYPE_OS_USERMODE_MAPPING,                                /*!< OS specific User mode mappings */
        
+       /* COMMON: */
+       RESMAN_TYPE_DEVICEMEM_CONTEXT,                                  /*!< Device Memory Context Resource */
+       RESMAN_TYPE_DEVICECLASSMEM_MAPPING,                             /*!< Device Memory Mapping Resource */
+       RESMAN_TYPE_DEVICEMEM_MAPPING,                                  /*!< Device Memory Mapping Resource */
+       RESMAN_TYPE_DEVICEMEM_WRAP,                                             /*!< Device Memory Wrap Resource */
+       RESMAN_TYPE_DEVICEMEM_ALLOCATION,                               /*!< Device Memory Allocation Resource */
+       RESMAN_TYPE_DEVICEMEM_ION,                                              /*!< Device Memory Ion Resource */
+       RESMAN_TYPE_EVENT_OBJECT,                                               /*!< Event Object */
+    RESMAN_TYPE_SHARED_MEM_INFO,                    /*!< Shared system memory meminfo */
+    RESMAN_TYPE_MODIFY_SYNC_OPS,                                       /*!< Syncobject synchronisation Resource*/
+    RESMAN_TYPE_SYNC_INFO,                                             /*!< Syncobject Resource*/
        
-       RESMAN_TYPE_KERNEL_DEVICEMEM_ALLOCATION                 
+       /* KERNEL: */
+       RESMAN_TYPE_KERNEL_DEVICEMEM_ALLOCATION                 /*!< Device Memory Allocation Resource */
 };
 
-#define RESMAN_CRITERIA_ALL                            0x00000000      
-#define RESMAN_CRITERIA_RESTYPE                        0x00000001      
-#define RESMAN_CRITERIA_PVOID_PARAM            0x00000002      
-#define RESMAN_CRITERIA_UI32_PARAM             0x00000004      
+#define RESMAN_CRITERIA_ALL                            0x00000000      /*!< match by criteria all */
+#define RESMAN_CRITERIA_RESTYPE                        0x00000001      /*!< match by criteria type */
+#define RESMAN_CRITERIA_PVOID_PARAM            0x00000002      /*!< match by criteria param1 */
+#define RESMAN_CRITERIA_UI32_PARAM             0x00000004      /*!< match by criteria param2 */
 
 typedef PVRSRV_ERROR (*RESMAN_FREE_FN)(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bForceCleanup); 
 
 typedef struct _RESMAN_ITEM_ *PRESMAN_ITEM;
 typedef struct _RESMAN_CONTEXT_ *PRESMAN_CONTEXT;
 
+/******************************************************************************
+ * resman functions 
+ *****************************************************************************/
+
+/*
+       Note:
+       Resource cleanup can fail with retry in which case we don't remove
+       it from resman's list and either UM or KM will try to release the
+       resource at a later date (and will keep trying until a non-retry
+       error is returned)
+*/
+
 PVRSRV_ERROR ResManInit(IMG_VOID);
 IMG_VOID ResManDeInit(IMG_VOID);
 
@@ -114,5 +144,9 @@ IMG_VOID PVRSRVResManDisconnect(PRESMAN_CONTEXT hResManContext,
 }
 #endif
 
-#endif 
+#endif /* __RESMAN_H__ */
+
+/******************************************************************************
+ End of file (resman.h)
+******************************************************************************/
 
index 2b5f197..d09b8a8 100644 (file)
@@ -1,28 +1,46 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Command queues and synchronisation
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Internal structures and definitions for command queues and 
+                synchronisation
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
 
 #ifndef SERVICES_HEADERS_H
 #define SERVICES_HEADERS_H
@@ -44,6 +62,7 @@
 #include "pvr_debug.h"
 #include "metrics.h"
 #include "osfunc.h"
+#include "refcount.h"
 
-#endif 
+#endif /* SERVICES_HEADERS_H */
 
index 474a1ee..5d396f8 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Services kernel module internal header file
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef SRVKM_H
 #define SRVKM_H
 extern "C" {
 #endif
 
-       
+       /**     Use PVR_DPF() unless message is necessary in release build
+        */
        #ifdef PVR_DISABLE_LOGGING
        #define PVR_LOG(X)
        #else
-        
+       /* PRQA S 3410 1 */ /* this macro requires no brackets in order to work */
        #define PVR_LOG(X)                      PVRSRVReleasePrintf X;
        #endif
 
@@ -58,7 +74,34 @@ extern "C" {
 }
 #endif
 
+/******************
+HIGHER LEVEL MACROS
+*******************/
+
+/*----------------------------------------------------------------------------
+Repeats the body of the loop for a certain minimum time, or until the body
+exits by its own means (break, return, goto, etc.)
+
+Example of usage:
+
+LOOP_UNTIL_TIMEOUT(MAX_HW_TIME_US)
+{
+       if(psQueueInfo->ui32ReadOffset == psQueueInfo->ui32WriteOffset)
+       {
+               bTimeout = IMG_FALSE;
+               break;
+       }
+       
+       OSWaitus(MAX_HW_TIME_US/WAIT_TRY_COUNT);
+} END_LOOP_UNTIL_TIMEOUT();
+
+-----------------------------------------------------------------------------*/
+
+/*     uiNotLastLoop will remain at 1 until the timeout has expired, at which time             
+ *     it will be decremented and the loop executed one final time. This is necessary
+ *     when preemption is enabled. 
+ */
+/* PRQA S 3411,3431 12 */ /* critical format, leave alone */
 #define LOOP_UNTIL_TIMEOUT(TIMEOUT) \
 {\
        IMG_UINT32 uiOffset, uiStart, uiCurrent; \
@@ -72,7 +115,15 @@ extern "C" {
 #define END_LOOP_UNTIL_TIMEOUT() \
 }
 
+/*!
+ ******************************************************************************
+
+ @Function             PVRSRVGetErrorStringKM
+
+ @Description  Returns a text string relating to the PVRSRV_ERROR enum.
+
+ ******************************************************************************/
 IMG_IMPORT
 const IMG_CHAR *PVRSRVGetErrorStringKM(PVRSRV_ERROR eError);
 
-#endif 
+#endif /* SRVKM_H */
index 9e04b88..cb70ff8 100644 (file)
@@ -1,29 +1,45 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Timed Trace header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description   Timed Trace header. Contines structures and functions used
+                in the timed trace subsystem.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #include "services_headers.h"
 #include "ttrace_common.h"
 #include "ttrace_tokens.h"
@@ -147,7 +163,7 @@ static INLINE IMG_VOID PVRSRVTimeTraceSysPhysAddr(IMG_UINT32 ui32Group, IMG_UINT
                                1, (IMG_UINT8 *) &psPAddr.uiAddr);
 }
 
-#else 
+#else /* defined(PVRSRV_NEED_PVR_TIME_TRACE) */
 
        #define PVR_TTRACE(group, class, token) \
                        ((void) 0)
@@ -170,7 +186,7 @@ static INLINE IMG_VOID PVRSRVTimeTraceSysPhysAddr(IMG_UINT32 ui32Group, IMG_UINT
        #define PVR_TTRACE_SYNC_OBJECT(group, token, syncobj, op) \
                        ((void) 0)
 
-#endif 
+#endif /* defined(PVRSRV_NEED_PVR_TIME_TRACE) */
 
 IMG_IMPORT PVRSRV_ERROR PVRSRVTimeTraceInit(IMG_VOID);
 IMG_IMPORT IMG_VOID PVRSRVTimeTraceDeinit(IMG_VOID);
@@ -181,4 +197,4 @@ IMG_IMPORT PVRSRV_ERROR PVRSRVTimeTraceBufferCreate(IMG_UINT32 ui32PID);
 IMG_IMPORT PVRSRV_ERROR PVRSRVTimeTraceBufferDestroy(IMG_UINT32 ui32PID);
 
 IMG_IMPORT IMG_VOID PVRSRVDumpTimeTraceBuffers(IMG_VOID);
-#endif 
+#endif /* __TTRACE_H__ */
index 5895b6c..b14f256 100644 (file)
@@ -1,34 +1,95 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Timed Trace header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description   Timed Trace common header. Contains shared defines and 
+                structures which are shared with the post processing tool.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
 
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #include "img_types.h"
 
 #ifndef __TTRACE_COMMON_H__
 #define __TTRACE_COMMON_H__
 
+/*
+ * Trace item
+ * ==========
+ *
+ * A trace item contains a trace header, a timestamp, a UID and a
+ * data header all of which are 32-bit and mandatory. If there
+ * is no data then the data header size is set to 0.
+ *
+ * Trace header
+ * ------------
+ * 31   27   23   19   15   11   7    3
+ * GGGG GGGG CCCC CCCC TTTT TTTT TTTT TTTT
+ *
+ * G = group
+ *     Note:
+ *     Group 0xff means the message is padding
+ *
+ * C = class
+ * T = Token
+ *
+ * Data header
+ *-----------
+ * 31   27   23   19   15   11   7    3
+ * SSSS SSSS SSSS SSSS TTTT CCCC CCCC CCCC
+ *
+ * S = data packet size
+ * T = Type
+ *             0000 - 8 bit
+ *             0001 - 16 bit
+ *             0010 - 32 bit
+ *             0011 - 64 bit
+ *
+ * C = data item count
+ *
+ * Note: It might look strange having both the packet
+ *       size and the data item count, but the idea
+ *       is the you might have a "special" data type
+ *       who's size might not be known by the post
+ *       processing program and rather then fail
+ *       processing the buffer after that point if we
+ *       know the size we can just skip it and move to
+ *       the next item.
+ */
+
+
 #define PVRSRV_TRACE_HEADER            0
 #define PVRSRV_TRACE_TIMESTAMP         1
 #define PVRSRV_TRACE_HOSTUID           2
 
 #define TIME_TRACE_BUFFER_SIZE         4096
 
+/* Type defines for trace items */
 #define PVRSRV_TRACE_TYPE_UI8          0
 #define PVRSRV_TRACE_TYPE_UI16         1
 #define PVRSRV_TRACE_TYPE_UI32         2
  #define PVRSRV_TRACE_SYNC_WO_DEV_VADDR        5
  #define PVRSRV_TRACE_SYNC_RO_DEV_VADDR        6
  #define PVRSRV_TRACE_SYNC_OP          7
-#define PVRSRV_TRACE_TYPE_SYNC_SIZE    ((PVRSRV_TRACE_SYNC_OP + 1) * sizeof(IMG_UINT32))
+ #define PVRSRV_TRACE_SYNC_RO2P                8
+ #define PVRSRV_TRACE_SYNC_RO2C                9
+ #define PVRSRV_TRACE_SYNC_RO2_DEV_VADDR 10
+#define PVRSRV_TRACE_TYPE_SYNC_SIZE    ((PVRSRV_TRACE_SYNC_RO2_DEV_VADDR + 1) * sizeof(IMG_UINT32))
 
-#endif 
+#endif /* __TTRACE_COMMON_H__*/
index 21ea5fb..24bc484 100644 (file)
@@ -1,32 +1,52 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Timed Trace header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description   Timed Trace token header. Contains defines for all the tokens 
+                used.
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef __TTRACE_TOKENS_H__
 #define __TTRACE_TOKENS_H__
 
+/* All defines should use decimal so to not confuse the post processing tool */
+
+/* Trace groups */
 #define PVRSRV_TRACE_GROUP_KICK                0
 #define PVRSRV_TRACE_GROUP_TRANSFER    1
 #define PVRSRV_TRACE_GROUP_QUEUE       2
@@ -35,6 +55,7 @@
 
 #define PVRSRV_TRACE_GROUP_PADDING     255
 
+/* Trace classes */
 #define PVRSRV_TRACE_CLASS_FUNCTION_ENTER      0
 #define PVRSRV_TRACE_CLASS_FUNCTION_EXIT       1
 #define PVRSRV_TRACE_CLASS_SYNC                        2
 #define PVRSRV_TRACE_CLASS_CMD_END             5
 #define PVRSRV_TRACE_CLASS_CMD_COMP_START      6
 #define PVRSRV_TRACE_CLASS_CMD_COMP_END                7
+#define PVRSRV_TRACE_CLASS_FLAGS                       8
 
 #define PVRSRV_TRACE_CLASS_NONE                        255
 
+/* Operation about to happen on the sync object */
 #define PVRSRV_SYNCOP_SAMPLE           0
 #define PVRSRV_SYNCOP_COMPLETE         1
 #define PVRSRV_SYNCOP_DUMP             2
 
+/*
+ * Trace tokens
+ * ------------
+ * These only need to unique within a group.
+ */
+
+/* Kick group tokens */
 #define KICK_TOKEN_DOKICK              0
 #define KICK_TOKEN_CCB_OFFSET          1
 #define KICK_TOKEN_TA3D_SYNC           2
 #define KICK_TOKEN_3D_SYNC             4
 #define KICK_TOKEN_SRC_SYNC            5
 #define KICK_TOKEN_DST_SYNC            6
+#define KICK_TOKEN_FIRST_KICK  7
+#define KICK_TOKEN_LAST_KICK   8
 
+/* Transfer Queue group tokens */
 #define TRANSFER_TOKEN_SUBMIT          0
 #define TRANSFER_TOKEN_TA_SYNC         1
 #define TRANSFER_TOKEN_3D_SYNC         2
@@ -65,6 +98,7 @@
 #define TRANSFER_TOKEN_DST_SYNC                4
 #define TRANSFER_TOKEN_CCB_OFFSET      5
 
+/* Queue group tokens */
 #define QUEUE_TOKEN_GET_SPACE          0
 #define QUEUE_TOKEN_INSERTKM           1
 #define QUEUE_TOKEN_SUBMITKM           2
 #define QUEUE_TOKEN_DST_SYNC           9
 #define QUEUE_TOKEN_COMMAND_TYPE       10
 
+/* uKernel Sync tokens */
 #define MKSYNC_TOKEN_KERNEL_CCB_OFFSET 0
 #define MKSYNC_TOKEN_CORE_CLK          1
 #define MKSYNC_TOKEN_UKERNEL_CLK       2
 
-#endif 
+#endif /* __TTRACE_TOKENS_H__ */
index 6131e13..5153a8b 100644 (file)
@@ -1,34 +1,51 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Common System APIs and structures
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    This header provides common system-specific declarations and macros
+                that are supported by all system's
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _SYSCOMMON_H
 #define _SYSCOMMON_H
 
-#include "sysconfig.h"      
-#include "sysinfo.h"           
+#include "sysconfig.h"      /* System specific system defines */
+#include "sysinfo.h"           /* globally accessible system info */
 #include "servicesint.h"
 #include "queue.h"
 #include "power.h"
 extern "C" {
 #endif
 
+/*!
+ ****************************************************************************
+       device id management structure
+ ****************************************************************************/
 typedef struct _SYS_DEVICE_ID_TAG
 {
        IMG_UINT32      uiID;
@@ -55,45 +76,53 @@ typedef struct _SYS_DEVICE_ID_TAG
 } SYS_DEVICE_ID;
 
 
+/*
+       the max number of independent local backing stores services supports
+       (grow this number if ever required)
+*/
 #define SYS_MAX_LOCAL_DEVMEM_ARENAS    4
 
 typedef IMG_HANDLE (*PFN_HTIMER_CREATE) (IMG_VOID);
 typedef IMG_UINT32 (*PFN_HTIMER_GETUS) (IMG_HANDLE);
 typedef IMG_VOID (*PFN_HTIMER_DESTROY) (IMG_HANDLE);
+/*!
+ ****************************************************************************
+       Top level system data structure
+ ****************************************************************************/
 typedef struct _SYS_DATA_TAG_
 {
-    IMG_UINT32                  ui32NumDevices;                
+    IMG_UINT32                  ui32NumDevices;                /*!< number of devices in system */
        SYS_DEVICE_ID                           sDeviceID[SYS_DEVICE_COUNT];
-    PVRSRV_DEVICE_NODE                 *psDeviceNodeList;                      
-    PVRSRV_POWER_DEV                   *psPowerDeviceList;                     
-       PVRSRV_RESOURCE                         sPowerStateChangeResource;      
-       PVRSRV_SYS_POWER_STATE          eCurrentPowerState;                     
-       PVRSRV_SYS_POWER_STATE          eFailedPowerState;                      
-       IMG_UINT32                                      ui32CurrentOSPowerState;        
-    PVRSRV_QUEUE_INFO           *psQueueList;                  
-       PVRSRV_KERNEL_SYNC_INFO         *psSharedSyncInfoList;          
-    IMG_PVOID                   pvEnvSpecificData;             
-    IMG_PVOID                   pvSysSpecificData;             
-       PVRSRV_RESOURCE                         sQProcessResource;                      
-       IMG_VOID                                        *pvSOCRegsBase;                         
-    IMG_HANDLE                  hSOCTimerRegisterOSMemHandle; 
-       IMG_UINT32                                      *pvSOCTimerRegisterKM;          
-       IMG_VOID                                        *pvSOCClockGateRegsBase;        
+    PVRSRV_DEVICE_NODE                 *psDeviceNodeList;                      /*!< list of private device info structures */
+    PVRSRV_POWER_DEV                   *psPowerDeviceList;                     /*!< list of devices registered with the power manager */
+       PVRSRV_RESOURCE                         sPowerStateChangeResource;      /*!< lock for power state transitions */
+       PVRSRV_SYS_POWER_STATE          eCurrentPowerState;                     /*!< current Kernel services power state */
+       PVRSRV_SYS_POWER_STATE          eFailedPowerState;                      /*!< Kernel services power state (Failed to transition to) */
+       IMG_UINT32                                      ui32CurrentOSPowerState;        /*!< current OS specific power state */
+    PVRSRV_QUEUE_INFO           *psQueueList;                  /*!< list of all command queues in the system */
+       PVRSRV_KERNEL_SYNC_INFO         *psSharedSyncInfoList;          /*!< list of cross process syncinfos */
+    IMG_PVOID                   pvEnvSpecificData;             /*!< Environment specific data */
+    IMG_PVOID                   pvSysSpecificData;             /*!< Unique to system, accessible at system layer only */
+       PVRSRV_RESOURCE                         sQProcessResource;                      /*!< Command Q processing access lock */
+       IMG_VOID                                        *pvSOCRegsBase;                         /*!< SOC registers base linear address */
+    IMG_HANDLE                  hSOCTimerRegisterOSMemHandle; /*!< SOC Timer register (if present) */
+       IMG_UINT32                                      *pvSOCTimerRegisterKM;          /*!< SOC Timer register (if present) */
+       IMG_VOID                                        *pvSOCClockGateRegsBase;        /*!< SOC Clock gating registers (if present) */
        IMG_UINT32                                      ui32SOCClockGateRegsSize;
                                                                                                                        
        struct _DEVICE_COMMAND_DATA_ *apsDeviceCommandData[SYS_DEVICE_COUNT];
-                                                                                                                       
+                                                                                                                       /*!< command complete data and callback function store for every command for every device */
 
-       RA_ARENA                                        *apsLocalDevMemArena[SYS_MAX_LOCAL_DEVMEM_ARENAS]; 
+       RA_ARENA                                        *apsLocalDevMemArena[SYS_MAX_LOCAL_DEVMEM_ARENAS]; /*!< RA Arenas for local device memory heap management */
 
-    IMG_CHAR                    *pszVersionString;          
+    IMG_CHAR                    *pszVersionString;          /*!< Human readable string showing relevent system version info */
 #if defined (SUPPORT_SID_INTERFACE)
-       PVRSRV_EVENTOBJECT_KM           *psGlobalEventObject;           
+       PVRSRV_EVENTOBJECT_KM           *psGlobalEventObject;           /*!< OS Global Event Object */
 #else
-       PVRSRV_EVENTOBJECT                      *psGlobalEventObject;           
+       PVRSRV_EVENTOBJECT                      *psGlobalEventObject;           /*!< OS Global Event Object */
 #endif
 
-       PVRSRV_MISC_INFO_CPUCACHEOP_TYPE ePendingCacheOpType;   
+       PVRSRV_MISC_INFO_CPUCACHEOP_TYPE ePendingCacheOpType;   /*!< Deferred CPU cache op control */
 
        PFN_HTIMER_CREATE       pfnHighResTimerCreate;
        PFN_HTIMER_GETUS        pfnHighResTimerGetus;
@@ -101,6 +130,13 @@ typedef struct _SYS_DATA_TAG_
 } SYS_DATA;
 
 
+/****************************************************************************
+ *     common function prototypes
+ ****************************************************************************/
+
+#if defined (CUSTOM_DISPLAY_SEGMENT)
+PVRSRV_ERROR SysGetDisplaySegmentAddress (IMG_VOID *pvDevInfo, IMG_VOID *pvPhysicalAddress, IMG_UINT32 *pui32Length);
+#endif
 
 PVRSRV_ERROR SysInitialise(IMG_VOID);
 PVRSRV_ERROR SysFinalise(IMG_VOID);
@@ -128,6 +164,10 @@ PVRSRV_ERROR SysDevicePostPowerState(IMG_UINT32 ui32DeviceIndex,
                                                                         PVRSRV_DEV_POWER_STATE eNewPowerState,
                                                                         PVRSRV_DEV_POWER_STATE eCurrentPowerState);
 
+#if defined(SYS_SUPPORTS_SGX_IDLE_CALLBACK)
+IMG_VOID SysSGXIdleTransition(IMG_BOOL bSGXIdle);
+#endif /* SYS_SUPPORTS_SGX_IDLE_CALLBACK */
+
 #if defined(SYS_CUSTOM_POWERLOCK_WRAP)
 PVRSRV_ERROR SysPowerLockWrap(IMG_BOOL bTryLock);
 IMG_VOID SysPowerLockUnwrap(IMG_VOID);
@@ -155,32 +195,71 @@ extern SYS_DATA* gpsSysData;
 
 #if !defined(USE_CODE)
 
+/*!
+******************************************************************************
+
+ @Function     SysAcquireData
+
+ @Description returns reference to to sysdata
+                               creating one on first call
+
+ @Input    ppsSysData - pointer to copy reference into
+
+ @Return   ppsSysData updated
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(SysAcquireData)
 #endif
 static INLINE IMG_VOID SysAcquireData(SYS_DATA **ppsSysData)
 {
-       
+       /* Copy pointer back system information pointer */
        *ppsSysData = gpsSysData;
 
-       
+       /*
+               Verify we've not been called before being initialised. Instinctively
+               we should do this check first, but in the failing case we'll just write
+               null back and the compiler won't warn about an uninitialised varible.
+       */
+       PVR_ASSERT (gpsSysData != IMG_NULL);
+}
+
 
+/*!
+******************************************************************************
 
+ @Function     SysAcquireDataNoCheck
 
-       PVR_ASSERT (gpsSysData != IMG_NULL);
-}
+ @Description returns reference to to sysdata
+                               creating one on first call
+
+ @Input    none
 
+ @Return   psSysData - pointer to copy reference into
 
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(SysAcquireDataNoCheck)
 #endif
 static INLINE SYS_DATA * SysAcquireDataNoCheck(IMG_VOID)
 {
-       
+       /* return pointer back system information pointer */
        return gpsSysData;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SysInitialiseCommon
+
+ @Description Performs system initialisation common to all systems
+
+ @Input    psSysData - pointer to system data
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(SysInitialiseCommon)
 #endif
@@ -188,39 +267,90 @@ static INLINE PVRSRV_ERROR SysInitialiseCommon(SYS_DATA *psSysData)
 {
        PVRSRV_ERROR    eError;
 
-       
+       /* Initialise Services */
        eError = PVRSRVInit(psSysData);
 
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     SysDeinitialiseCommon
+
+ @Description Performs system deinitialisation common to all systems
+
+ @Input    psSysData - pointer to system data
+
+ @Return   PVRSRV_ERROR  :
+
+******************************************************************************/
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(SysDeinitialiseCommon)
 #endif
 static INLINE IMG_VOID SysDeinitialiseCommon(SYS_DATA *psSysData)
 {
-       
+       /* De-initialise Services */
        PVRSRVDeInit(psSysData);
 
        OSDestroyResource(&psSysData->sPowerStateChangeResource);
 }
-#endif 
+#endif /* !defined(USE_CODE) */
 
 
+/*
+ * SysReadHWReg and SysWriteHWReg differ from OSReadHWReg and OSWriteHWReg
+ * in that they are always intended for use with real hardware, even on
+ * NO_HARDWARE systems.
+ */
 #if !(defined(NO_HARDWARE) && defined(__linux__) && defined(__KERNEL__))
 #define        SysReadHWReg(p, o) OSReadHWReg(p, o)
 #define SysWriteHWReg(p, o, v) OSWriteHWReg(p, o, v)
-#else  
+#else  /* !(defined(NO_HARDWARE) && defined(__linux__)) */
+/*!
+******************************************************************************
+
+ @Function     SysReadHWReg
+
+ @Description
+
+ register read function
+
+ @input pvLinRegBaseAddr :     lin addr of register block base
+
+ @input ui32Offset :
+
+ @Return   register value
+
+******************************************************************************/
 static inline IMG_UINT32 SysReadHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset)
 {
        return (IMG_UINT32) readl(pvLinRegBaseAddr + ui32Offset);
 }
 
+/*!
+******************************************************************************
+
+ @Function     SysWriteHWReg
+
+ @Description
+
+ register write function
+
+ @input pvLinRegBaseAddr :     lin addr of register block base
+
+ @input ui32Offset :
+
+ @input ui32Value :
+
+ @Return   none
+
+******************************************************************************/
 static inline IMG_VOID SysWriteHWReg(IMG_PVOID pvLinRegBaseAddr, IMG_UINT32 ui32Offset, IMG_UINT32 ui32Value)
 {
        writel(ui32Value, pvLinRegBaseAddr + ui32Offset);
 }
-#endif 
+#endif /* !(defined(NO_HARDWARE) && defined(__linux__)) */
 
 #if defined(__cplusplus)
 }
@@ -260,3 +390,6 @@ static INLINE IMG_VOID SysHighResTimerDestroy(IMG_HANDLE hTimer)
 }
 #endif
 
+/*****************************************************************************
+ End of file (syscommon.h)
+*****************************************************************************/
index dd91bb6..1513950 100644 (file)
@@ -471,6 +471,7 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                OSReservePhys(TimerRegPhysBase,
                                  4,
                                  PVRSRV_HAP_MULTI_PROCESS|PVRSRV_HAP_UNCACHED,
+                                 IMG_NULL,                                             
                                  (IMG_VOID **)&gpsSysData->pvSOCTimerRegisterKM,
                                  &gpsSysData->hSOCTimerRegisterOSMemHandle);
        }
index dd91bb6..db58824 100644 (file)
@@ -471,6 +471,7 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                OSReservePhys(TimerRegPhysBase,
                                  4,
                                  PVRSRV_HAP_MULTI_PROCESS|PVRSRV_HAP_UNCACHED,
+                                 IMG_NULL,
                                  (IMG_VOID **)&gpsSysData->pvSOCTimerRegisterKM,
                                  &gpsSysData->hSOCTimerRegisterOSMemHandle);
        }
index b6d3f5a..e42b36b 100644 (file)
@@ -36,6 +36,6 @@
 #endif
 
 
-#define SYS_DEVICE_COUNT 15 
+#define SYS_DEVICE_COUNT 15
 
 #endif 
index c8eea1e..0902042 100644 (file)
@@ -1,28 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          SGX kernel/client driver interface structures and prototypes
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined(__OEMFUNCS_H__)
 #define __OEMFUNCS_H__
 extern "C" {
 #endif
 
+/* function in/out data structures: */
 typedef IMG_UINT32   (*PFN_SRV_BRIDGEDISPATCH)( IMG_UINT32  Ioctl,
                                                                                                IMG_BYTE   *pInBuf,
                                                                                                IMG_UINT32  InBufLen, 
                                                                                            IMG_BYTE   *pOutBuf,
                                                                                                IMG_UINT32  OutBufLen,
                                                                                                IMG_UINT32 *pdwBytesTransferred);
+/*
+       Function table for kernel 3rd party driver to kernel services
+*/
 typedef struct PVRSRV_DC_OEM_JTABLE_TAG
 {
        PFN_SRV_BRIDGEDISPATCH                  pfnOEMBridgeDispatch;
@@ -52,5 +71,10 @@ typedef struct PVRSRV_DC_OEM_JTABLE_TAG
 }
 #endif
 
-#endif 
+#endif /* __OEMFUNCS_H__ */
+
+/*****************************************************************************
+ End of file (oemfuncs.h)
+*****************************************************************************/
+
 
index 39bc7a1..a82f1b2 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          System Configuration
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    System Configuration functions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "sysconfig.h"
 #include "services_headers.h"
 
 #include "ocpdefs.h"
 
+/* top level system data anchor point*/
 SYS_DATA* gpsSysData = (SYS_DATA*)IMG_NULL;
 SYS_DATA  gsSysData;
 
 static SYS_SPECIFIC_DATA gsSysSpecificData;
 SYS_SPECIFIC_DATA *gpsSysSpecificData;
 
-static IMG_UINT32      gui32SGXDeviceID;
-static SGX_DEVICE_MAP  gsSGXDeviceMap;
-static PVRSRV_DEVICE_NODE *gpsSGXDevNode;
+/* SGX structures */
+static IMG_UINT32                      gui32SGXDeviceID;
+static SGX_DEVICE_MAP          gsSGXDeviceMap;
+static PVRSRV_DEVICE_NODE      *gpsSGXDevNode;
 
-#define DEVICE_SGX_INTERRUPT (1 << 0)
 
 #if defined(NO_HARDWARE) || defined(SGX_OCP_REGS_ENABLED)
 static IMG_CPU_VIRTADDR gsSGXRegsCPUVAddr;
@@ -79,14 +96,14 @@ static PVRSRV_ERROR EnableSGXClocksWrap(SYS_DATA *psSysData)
        return eError;
 }
 
-#else 
+#else /* defined(SGX_OCP_REGS_ENABLED) */
 
 static INLINE PVRSRV_ERROR EnableSGXClocksWrap(SYS_DATA *psSysData)
 {
        return EnableSGXClocks(psSysData);
 }
 
-#endif 
+#endif /* defined(SGX_OCP_REGS_ENABLED) */
 
 static INLINE PVRSRV_ERROR EnableSystemClocksWrap(SYS_DATA *psSysData)
 {
@@ -95,7 +112,10 @@ static INLINE PVRSRV_ERROR EnableSystemClocksWrap(SYS_DATA *psSysData)
 #if !defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
        if(eError == PVRSRV_OK)
        {
-               
+               /*
+                * The SGX Clocks are enabled separately if active power
+                * management is enabled.
+                */
                eError = EnableSGXClocksWrap(psSysData);
                if (eError != PVRSRV_OK)
                {
@@ -107,6 +127,18 @@ static INLINE PVRSRV_ERROR EnableSystemClocksWrap(SYS_DATA *psSysData)
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function     SysLocateDevices
+
+ @Description  Specifies devices in the systems memory map
+
+ @Input                psSysData - sys data
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
 {
 #if defined(NO_HARDWARE)
@@ -121,12 +153,16 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
 
        PVR_UNREFERENCED_PARAMETER(psSysData);
 
-       
+       /* SGX Device: */
        gsSGXDeviceMap.ui32Flags = 0x0;
        
 #if defined(NO_HARDWARE)
-       
-       
+       /* 
+        * For no hardware, allocate some contiguous memory for the
+        * register block.
+        */
+
+       /* Registers */
        gsSGXDeviceMap.ui32RegsSize = SYS_OMAP4430_SGX_REGS_SIZE;
 
        eError = OSBaseAllocContigMemory(gsSGXDeviceMap.ui32RegsSize,
@@ -139,23 +175,27 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
        gsSGXDeviceMap.sRegsCpuPBase = sCpuPAddr;
        gsSGXDeviceMap.sRegsSysPBase = SysCpuPAddrToSysPAddr(gsSGXDeviceMap.sRegsCpuPBase);
 #if defined(__linux__)
-       
+       /* Indicate the registers are already mapped */
        gsSGXDeviceMap.pvRegsCpuVBase = gsSGXRegsCPUVAddr;
 #else
-       
+       /*
+        * FIXME: Could we just use the virtual address returned by
+        * OSBaseAllocContigMemory?
+        */
        gsSGXDeviceMap.pvRegsCpuVBase = IMG_NULL;
 #endif
 
        OSMemSet(gsSGXRegsCPUVAddr, 0, gsSGXDeviceMap.ui32RegsSize);
 
-       
-
-
+       /*
+               device interrupt IRQ
+               Note: no interrupts available on no hardware system
+       */
        gsSGXDeviceMap.ui32IRQ = 0;
 
-#else 
+#else /* defined(NO_HARDWARE) */
 #if defined(PVR_LINUX_DYNAMIC_SGX_RESOURCE_INFO)
-       
+       /* get the resource and IRQ through platform resource API */
        dev_res = platform_get_resource(gpsPVRLDMDev, IORESOURCE_MEM, 0);
        if (dev_res == NULL)
        {
@@ -180,14 +220,14 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
 
        gsSGXDeviceMap.ui32IRQ = dev_irq;
        PVR_TRACE(("SGX IRQ: %d", gsSGXDeviceMap.ui32IRQ));
-#else  
+#else  /* defined(PVR_LINUX_DYNAMIC_SGX_RESOURCE_INFO) */
        gsSGXDeviceMap.sRegsSysPBase.uiAddr = SYS_OMAP4430_SGX_REGS_SYS_PHYS_BASE;
        gsSGXDeviceMap.sRegsCpuPBase = SysSysPAddrToCpuPAddr(gsSGXDeviceMap.sRegsSysPBase);
        gsSGXDeviceMap.ui32RegsSize = SYS_OMAP4430_SGX_REGS_SIZE;
 
        gsSGXDeviceMap.ui32IRQ = SYS_OMAP4430_SGX_IRQ;
 
-#endif 
+#endif /* defined(PVR_LINUX_DYNAMIC_SGX_RESOURCE_INFO) */
 #if defined(SGX_OCP_REGS_ENABLED)
        gsSGXRegsCPUVAddr = OSMapPhysToLin(gsSGXDeviceMap.sRegsCpuPBase,
        gsSGXDeviceMap.ui32RegsSize,
@@ -200,27 +240,37 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
                return PVRSRV_ERROR_BAD_MAPPING;
        }
 
-       
+       /* Indicate the registers are already mapped */
        gsSGXDeviceMap.pvRegsCpuVBase = gsSGXRegsCPUVAddr;
        gpvOCPRegsLinAddr = gsSGXRegsCPUVAddr;
 #endif
-#endif 
+#endif /* defined(NO_HARDWARE) */
 
 #if defined(PDUMP)
        {
-               
+               /* initialise memory region name for pdumping */
                static IMG_CHAR pszPDumpDevName[] = "SGXMEM";
                gsSGXDeviceMap.pszPDumpDevName = pszPDumpDevName;
        }
 #endif
 
-       
+       /* add other devices here: */
 
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SysCreateVersionString
+
+ @Description Read the version string 
+
+ @Return   IMG_CHAR *  : Version string
+
+******************************************************************************/
 static IMG_CHAR *SysCreateVersionString(void)
 {
        static IMG_CHAR aszVersionString[100];
@@ -273,6 +323,16 @@ static IMG_CHAR *SysCreateVersionString(void)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SysInitialise
+ @Description Initialises kernel services at 'driver load' time
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR SysInitialise(IMG_VOID)
 {
        IMG_UINT32                      i;
@@ -304,7 +364,7 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
 
        gpsSysData->ui32NumDevices = SYS_DEVICE_COUNT;
 
-       
+       /* init device ID's */
        for(i=0; i<SYS_DEVICE_COUNT; i++)
        {
                gpsSysData->sDeviceID[i].uiID = i;
@@ -324,7 +384,7 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
        }
 
 #if !defined(SGX_DYNAMIC_TIMING_INFO)
-       
+       /* Set up timing information*/
        psTimingInfo = &gsSGXDeviceMap.sTimingInfo;
        psTimingInfo->ui32CoreClockSpeed = SYS_SGX_CLOCK_SPEED;
        psTimingInfo->ui32HWRecoveryFreq = SYS_SGX_HWRECOVERY_TIMEOUT_FREQ; 
@@ -332,19 +392,21 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
        psTimingInfo->bEnableActivePM = IMG_TRUE;
 #else  
        psTimingInfo->bEnableActivePM = IMG_FALSE;
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
        psTimingInfo->ui32ActivePowManLatencyms = SYS_SGX_ACTIVE_POWER_LATENCY_MS; 
        psTimingInfo->ui32uKernelFreq = SYS_SGX_PDS_TIMER_FREQ; 
 #endif
 
-       
-
+       /*
+               Setup the Source Clock Divider value
+       */
        gpsSysSpecificData->ui32SrcClockDiv = 3;
 
-       
-
-
-
+       /*
+               Locate the devices within the system, specifying 
+               the physical addresses of each devices components 
+               (regs, mem, ports etc.)
+       */
        eError = SysLocateDevices(gpsSysData);
        if (eError != PVRSRV_OK)
        {
@@ -365,9 +427,20 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
        }
        SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_PM_RUNTIME);
 
-       
-
+       eError = SysDvfsInitialize(gpsSysSpecificData);
+       if (eError != PVRSRV_OK)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"SysInitialise: Failed to initialize DVFS"));
+               (IMG_VOID)SysDeinitialise(gpsSysData);
+               gpsSysData = IMG_NULL;
+               return eError;
+       }
+       SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_DVFS_INIT);
 
+       /*
+               Register devices with the system
+               This also sets up their memory maps/heaps
+       */
        eError = PVRSRVRegisterDevice(gpsSysData, SGXRegisterDevice,
                                                                  DEVICE_SGX_INTERRUPT, &gui32SGXDeviceID);
        if (eError != PVRSRV_OK)
@@ -379,14 +452,14 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
        }
        SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_REGDEV);
 
-       
-
-
-       
+       /*
+               Once all devices are registered, specify the backing store
+               and, if required, customise the memory heap config
+       */      
        psDeviceNode = gpsSysData->psDeviceNodeList;
        while(psDeviceNode)
        {
-               
+               /* perform any OEM SOC address space customisations here */
                switch(psDeviceNode->sDevId.eDeviceType)
                {
                        case PVRSRV_DEVICE_TYPE_SGX:
@@ -394,16 +467,17 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                                DEVICE_MEMORY_INFO *psDevMemoryInfo;
                                DEVICE_MEMORY_HEAP_INFO *psDeviceMemoryHeap;
 
-                               
-
-
+                               /* 
+                                       specify the backing store to use for the devices MMU PT/PDs
+                                       - the PT/PDs are always UMA in this system
+                               */
                                psDeviceNode->psLocalDevMemArena = IMG_NULL;
 
-                               
+                               /* useful pointers */
                                psDevMemoryInfo = &psDeviceNode->sDevMemoryInfo;
                                psDeviceMemoryHeap = psDevMemoryInfo->psDeviceMemoryHeap;
 
-                               
+                               /* specify the backing store for all SGX heaps */
                                for(i=0; i<psDevMemoryInfo->ui32HeapCount; i++)
                                {
                                        psDeviceMemoryHeap[i].ui32Attribs |= PVRSRV_BACKINGSTORE_SYSMEM_NONCONTIG;
@@ -419,7 +493,7 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                                return PVRSRV_ERROR_INIT_FAILURE;
                }
 
-               
+               /* advance to next device */
                psDeviceNode = psDeviceNode->psNext;
        }
 
@@ -441,7 +515,7 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                gpsSysData = IMG_NULL;
                return eError;
        }
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
 
        eError = PVRSRVInitialiseDevice(gui32SGXDeviceID);
        if (eError != PVRSRV_OK)
@@ -454,9 +528,9 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
        SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_INITDEV);
 
 #if defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
-       
+       /* SGX defaults to D3 power state */
        DisableSGXClocks(gpsSysData);
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
 
 #if !defined(PVR_NO_OMAP_TIMER)
 #if defined(PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA)
@@ -471,15 +545,27 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                OSReservePhys(TimerRegPhysBase,
                                  4,
                                  PVRSRV_HAP_MULTI_PROCESS|PVRSRV_HAP_UNCACHED,
+                                 IMG_NULL,
                                  (IMG_VOID **)&gpsSysData->pvSOCTimerRegisterKM,
                                  &gpsSysData->hSOCTimerRegisterOSMemHandle);
        }
-#endif 
+#endif /* !defined(PVR_NO_OMAP_TIMER) */
+
 
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SysFinalise
+ @Description Final part of initialisation at 'driver load' time
+ @Return   PVRSRV_ERROR  : 
+
+******************************************************************************/
 PVRSRV_ERROR SysFinalise(IMG_VOID)
 {
        PVRSRV_ERROR eError = PVRSRV_OK;
@@ -491,7 +577,7 @@ PVRSRV_ERROR SysFinalise(IMG_VOID)
                PVR_DPF((PVR_DBG_ERROR,"SysFinalise: Failed to Enable SGX clocks (%d)", eError));
                return eError;
        }
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
 
        eError = OSInstallMISR(gpsSysData);
        if (eError != PVRSRV_OK)
@@ -502,7 +588,7 @@ PVRSRV_ERROR SysFinalise(IMG_VOID)
        SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_MISR);
 
 #if defined(SYS_USING_INTERRUPTS)
-       
+       /* install a Device ISR */
        eError = OSInstallDeviceLISR(gpsSysData, gsSGXDeviceMap.ui32IRQ, "SGX ISR", gpsSGXDevNode);
        if (eError != PVRSRV_OK)
        {
@@ -510,10 +596,12 @@ PVRSRV_ERROR SysFinalise(IMG_VOID)
                return eError;
        }
        SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_LISR);
-#endif 
-
+#if !defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
+       SysEnableSGXInterrupts(gpsSysData);
+#endif
+#endif /* defined(SYS_USING_INTERRUPTS) */
 #if defined(__linux__)
-       
+       /* Create a human readable version string for this system */
        gpsSysData->pszVersionString = SysCreateVersionString();
        if (!gpsSysData->pszVersionString)
        {
@@ -526,9 +614,9 @@ PVRSRV_ERROR SysFinalise(IMG_VOID)
 #endif
 
 #if defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
-       
+       /* SGX defaults to D3 power state */
        DisableSGXClocks(gpsSysData);
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
 
        gpsSysSpecificData->bSGXInitComplete = IMG_TRUE;
 
@@ -536,10 +624,22 @@ PVRSRV_ERROR SysFinalise(IMG_VOID)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SysDeinitialise
+
+ @Description  De-initialises kernel services at 'driver unload' time
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
 {
        PVRSRV_ERROR eError;
 
+       PVR_UNREFERENCED_PARAMETER(psSysData);
+
        if(gpsSysData->pvSOCTimerRegisterKM)
        {
                OSUnReservePhys(gpsSysData->pvSOCTimerRegisterKM,
@@ -548,10 +648,11 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
                                                gpsSysData->hSOCTimerRegisterOSMemHandle);
        }
 
+
 #if defined(SYS_USING_INTERRUPTS)
        if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_LISR))
        {
-               eError = OSUninstallDeviceLISR(psSysData);
+               eError = OSUninstallDeviceLISR(gpsSysData);
                if (eError != PVRSRV_OK)
                {
                        PVR_DPF((PVR_DBG_ERROR,"SysDeinitialise: OSUninstallDeviceLISR failed"));
@@ -562,7 +663,7 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
 
        if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_MISR))
        {
-               eError = OSUninstallMISR(psSysData);
+               eError = OSUninstallMISR(gpsSysData);
                if (eError != PVRSRV_OK)
                {
                        PVR_DPF((PVR_DBG_ERROR,"SysDeinitialise: OSUninstallMISR failed"));
@@ -574,16 +675,16 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
        {
 #if defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
                PVR_ASSERT(SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_SYSCLOCKS));
-               
+               /* Reenable SGX clocks whilst SGX is being deinitialised. */
                eError = EnableSGXClocksWrap(gpsSysData);
                if (eError != PVRSRV_OK)
                {
                        PVR_DPF((PVR_DBG_ERROR,"SysDeinitialise: EnableSGXClocks failed"));
                        return eError;
                }
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
 
-               
+               /* Deinitialise SGX */
                eError = PVRSRVDeinitialiseDevice (gui32SGXDeviceID);
                if (eError != PVRSRV_OK)
                {
@@ -592,6 +693,17 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
                }
        }
 
+       if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_DVFS_INIT))
+       {
+               eError = SysDvfsDeinitialize(gpsSysSpecificData);
+               if (eError != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,"SysDeinitialise: Failed to de-init DVFS"));
+                       gpsSysData = IMG_NULL;
+                       return eError;
+               }
+       }
+
        if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_PM_RUNTIME))
        {
                eError = SysPMRuntimeUnregister();
@@ -603,8 +715,9 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
                }
        }
 
-       
-
+       /*
+               Disable system clocks - must happen after last access to hardware.
+        */
        if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_SYSCLOCKS))
        {
                DisableSystemClocks(gpsSysData);
@@ -626,7 +739,7 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
        if(gsSGXRegsCPUVAddr != IMG_NULL)
        {
 #if defined(NO_HARDWARE)
-               
+               /* Free hardware resources. */
                OSBaseFreeContigMemory(SYS_OMAP4430_SGX_REGS_SIZE, gsSGXRegsCPUVAddr, gsSGXDeviceMap.sRegsCpuPBase);
 #else
 #if defined(SGX_OCP_REGS_ENABLED)
@@ -637,11 +750,11 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
 
                gpvOCPRegsLinAddr = IMG_NULL;
 #endif
-#endif 
+#endif /* defined(NO_HARDWARE) */
                gsSGXRegsCPUVAddr = IMG_NULL;
                gsSGXDeviceMap.pvRegsCpuVBase = gsSGXRegsCPUVAddr;
        }
-#endif 
+#endif /* defined(NO_HARDWARE) || defined(SGX_OCP_REGS_ENABLED) */
 
        
        gpsSysSpecificData->ui32SysSpecificData = 0;
@@ -653,6 +766,19 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function             SysGetDeviceMemoryMap
+
+ @Description  returns a device address map for the specified device
+
+ @Input                        eDeviceType - device type
+ @Input                        ppvDeviceMap - void ptr to receive device specific info.
+
+ @Return               PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR SysGetDeviceMemoryMap(PVRSRV_DEVICE_TYPE  eDeviceType,
                                                                   IMG_VOID                             **ppvDeviceMap)
 {
@@ -661,7 +787,7 @@ PVRSRV_ERROR SysGetDeviceMemoryMap(PVRSRV_DEVICE_TYPE       eDeviceType,
        {
                case PVRSRV_DEVICE_TYPE_SGX:
                {
-                       
+                       /* just return a pointer to the structure */
                        *ppvDeviceMap = (IMG_VOID*)&gsSGXDeviceMap;
 
                        break;
@@ -675,6 +801,20 @@ PVRSRV_ERROR SysGetDeviceMemoryMap(PVRSRV_DEVICE_TYPE      eDeviceType,
 }
 
 
+/*!
+******************************************************************************
+ @Function        SysCpuPAddrToDevPAddr
+
+ @Description     Compute a device physical address from a cpu physical
+                  address. Relevant when
+
+ @Input           cpu_paddr - cpu physical address.
+ @Input           eDeviceType - device type required if DevPAddr
+                                address spaces vary across devices
+                                in the same system
+ @Return         device physical address.
+
+******************************************************************************/
 IMG_DEV_PHYADDR SysCpuPAddrToDevPAddr(PVRSRV_DEVICE_TYPE       eDeviceType,
                                                                          IMG_CPU_PHYADDR               CpuPAddr)
 {
@@ -682,98 +822,205 @@ IMG_DEV_PHYADDR SysCpuPAddrToDevPAddr(PVRSRV_DEVICE_TYPE eDeviceType,
 
        PVR_UNREFERENCED_PARAMETER(eDeviceType);
 
-       
+       /* Note: for UMA system we assume DevP == CpuP */
        DevPAddr.uiAddr = CpuPAddr.uiAddr;
        
        return DevPAddr;
 }
 
+/*!
+******************************************************************************
+ @Function        SysSysPAddrToCpuPAddr
+
+ @Description     Compute a cpu physical address from a system physical
+                  address.
+
+ @Input           sys_paddr - system physical address.
+ @Return          cpu physical address.
+
+******************************************************************************/
 IMG_CPU_PHYADDR SysSysPAddrToCpuPAddr (IMG_SYS_PHYADDR sys_paddr)
 {
        IMG_CPU_PHYADDR cpu_paddr;
 
-       
+       /* This would only be an inequality if the CPU's MMU did not point to
+          sys address 0, ie. multi CPU system */
        cpu_paddr.uiAddr = sys_paddr.uiAddr;
        return cpu_paddr;
 }
 
+/*!
+******************************************************************************
+ @Function        SysCpuPAddrToSysPAddr
+
+ @Description     Compute a system physical address from a cpu physical
+                   address.
+
+ @Input           cpu_paddr - cpu physical address.
+ @Return          device physical address.
+
+******************************************************************************/
 IMG_SYS_PHYADDR SysCpuPAddrToSysPAddr (IMG_CPU_PHYADDR cpu_paddr)
 {
        IMG_SYS_PHYADDR sys_paddr;
 
-       
+       /* This would only be an inequality if the CPU's MMU did not point to
+          sys address 0, ie. multi CPU system */
        sys_paddr.uiAddr = cpu_paddr.uiAddr;
        return sys_paddr;
 }
 
 
+/*!
+******************************************************************************
+ @Function        SysSysPAddrToDevPAddr
+
+ @Description     Compute a device physical address from a system physical
+                   address.
+
+ @Input           SysPAddr - system physical address.
+ @Input           eDeviceType - device type required if DevPAddr 
+                               address spaces vary across devices 
+                               in the same system
+
+ @Return        Device physical address.
+
+******************************************************************************/
 IMG_DEV_PHYADDR SysSysPAddrToDevPAddr(PVRSRV_DEVICE_TYPE eDeviceType, IMG_SYS_PHYADDR SysPAddr)
 {
        IMG_DEV_PHYADDR DevPAddr;
 
        PVR_UNREFERENCED_PARAMETER(eDeviceType);
 
-       
+       /* Note: for UMA system we assume DevP == CpuP */
        DevPAddr.uiAddr = SysPAddr.uiAddr;
 
        return DevPAddr;
 }
 
 
+/*!
+******************************************************************************
+ @Function        SysDevPAddrToSysPAddr
+
+ @Description     Compute a device physical address from a system physical
+                   address.
+
+ @Input           DevPAddr - device physical address.
+ @Input           eDeviceType - device type required if DevPAddr 
+                 address spaces vary across devices 
+                 in the same system
+
+ @Return        System physical address.
+
+******************************************************************************/
 IMG_SYS_PHYADDR SysDevPAddrToSysPAddr(PVRSRV_DEVICE_TYPE eDeviceType, IMG_DEV_PHYADDR DevPAddr)
 {
        IMG_SYS_PHYADDR SysPAddr;
 
        PVR_UNREFERENCED_PARAMETER(eDeviceType);
 
-       
+       /* Note: for UMA system we assume DevP == SysP */
        SysPAddr.uiAddr = DevPAddr.uiAddr;
 
        return SysPAddr;
 }
 
 
+/*****************************************************************************
+ @Function        SysRegisterExternalDevice
+
+ @Description     Called when a 3rd party device registers with services
+
+ @Input           psDeviceNode - the new device node.
+
+ @Return        IMG_VOID
+*****************************************************************************/
 IMG_VOID SysRegisterExternalDevice(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        PVR_UNREFERENCED_PARAMETER(psDeviceNode);
 }
 
 
+/*****************************************************************************
+ @Function        SysRemoveExternalDevice
+
+ @Description     Called when a 3rd party device unregisters from services
+
+ @Input           psDeviceNode - the device node being removed.
+
+ @Return        IMG_VOID
+*****************************************************************************/
 IMG_VOID SysRemoveExternalDevice(PVRSRV_DEVICE_NODE *psDeviceNode)
 {
        PVR_UNREFERENCED_PARAMETER(psDeviceNode);
 }
 
+/*!
+******************************************************************************
+ @Function        SysGetInterruptSource
+
+ @Description     Returns System specific information about the device(s) that
+                               generated the interrupt in the system
+
+ @Input           psSysData
+ @Input           psDeviceNode
 
+ @Return        System specific information indicating which device(s) 
+                               generated the interrupt
+
+******************************************************************************/
 IMG_UINT32 SysGetInterruptSource(SYS_DATA                      *psSysData,
                                                                 PVRSRV_DEVICE_NODE     *psDeviceNode)
 {
        PVR_UNREFERENCED_PARAMETER(psSysData);
 #if defined(NO_HARDWARE)
-       
+       /* no interrupts in no_hw system just return all bits */
        return 0xFFFFFFFF;
 #else
-       
+       /* Not a shared irq, so we know this is an interrupt for this device */
        return psDeviceNode->ui32SOCInterruptBit;
 #endif
 }
 
 
+/*!
+******************************************************************************
+ @Function        SysClearInterrupts
+
+ @Description     Clears specified system interrupts
+
+ @Input           psSysData
+ @Input           ui32ClearBits
+
+ @Return        IMG_VOID
+
+******************************************************************************/
 IMG_VOID SysClearInterrupts(SYS_DATA* psSysData, IMG_UINT32 ui32ClearBits)
 {
        PVR_UNREFERENCED_PARAMETER(ui32ClearBits);
-#if defined(NO_HARDWARE)
        PVR_UNREFERENCED_PARAMETER(psSysData);
-#else
+#if !defined(NO_HARDWARE)
 #if defined(SGX_OCP_NO_INT_BYPASS)
        OSWriteHWReg(gpvOCPRegsLinAddr, EUR_CR_OCP_IRQSTATUS_2, 0x1);
 #endif
-       
+       /* Flush posted writes */
        OSReadHWReg(((PVRSRV_SGXDEV_INFO *)gpsSGXDevNode->pvDevice)->pvRegsBaseKM, EUR_CR_EVENT_HOST_CLEAR);
-#endif 
+#endif /* defined(NO_HARDWARE) */
 }
 
 #if defined(SGX_OCP_NO_INT_BYPASS)
+/*!
+******************************************************************************
+ @Function        SysEnableSGXInterrupts
+
+ @Description     Enables SGX interrupts
+
+ @Input           psSysData
+
+ @Return        IMG_VOID
+
+******************************************************************************/
 IMG_VOID SysEnableSGXInterrupts(SYS_DATA *psSysData)
 {
        SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *)psSysData->pvSysSpecificData;
@@ -785,6 +1032,17 @@ IMG_VOID SysEnableSGXInterrupts(SYS_DATA *psSysData)
        }
 }
 
+/*!
+******************************************************************************
+ @Function        SysDisableSGXInterrupts
+
+ @Description     Disables SGX interrupts
+
+ @Input           psSysData
+
+ @Return        IMG_VOID
+
+******************************************************************************/
 IMG_VOID SysDisableSGXInterrupts(SYS_DATA *psSysData)
 {
        SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *)psSysData->pvSysSpecificData;
@@ -795,8 +1053,20 @@ IMG_VOID SysDisableSGXInterrupts(SYS_DATA *psSysData)
                SYS_SPECIFIC_DATA_CLEAR(psSysSpecData, SYS_SPECIFIC_DATA_IRQ_ENABLED);
        }
 }
-#endif 
+#endif /* defined(SGX_OCP_NO_INT_BYPASS) */
 
+/*!
+******************************************************************************
+
+ @Function     SysSystemPrePowerState
+
+ @Description  Perform system-level processing required before a power transition
+
+ @Input                eNewPowerState :
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR SysSystemPrePowerState(PVRSRV_SYS_POWER_STATE eNewPowerState)
 {
        PVRSRV_ERROR eError = PVRSRV_OK;
@@ -841,6 +1111,18 @@ PVRSRV_ERROR SysSystemPrePowerState(PVRSRV_SYS_POWER_STATE eNewPowerState)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SysSystemPostPowerState
+
+ @Description  Perform system-level processing required after a power transition
+
+ @Input                eNewPowerState :
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR SysSystemPostPowerState(PVRSRV_SYS_POWER_STATE eNewPowerState)
 {
        PVRSRV_ERROR eError = PVRSRV_OK;
@@ -889,6 +1171,21 @@ PVRSRV_ERROR SysSystemPostPowerState(PVRSRV_SYS_POWER_STATE eNewPowerState)
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SysDevicePrePowerState
+
+ @Description  Perform system level processing required before a device power
+                               transition
+
+ @Input                ui32DeviceIndex :
+ @Input                eNewPowerState :
+ @Input                eCurrentPowerState :
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR SysDevicePrePowerState(IMG_UINT32                         ui32DeviceIndex,
                                                                        PVRSRV_DEV_POWER_STATE  eNewPowerState,
                                                                        PVRSRV_DEV_POWER_STATE  eCurrentPowerState)
@@ -906,13 +1203,28 @@ PVRSRV_ERROR SysDevicePrePowerState(IMG_UINT32                           ui32DeviceIndex,
                PVR_DPF((PVR_DBG_MESSAGE, "SysDevicePrePowerState: SGX Entering state D3"));
                DisableSGXClocks(gpsSysData);
        }
-#else  
+#else  /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
        PVR_UNREFERENCED_PARAMETER(eNewPowerState );
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function     SysDevicePostPowerState
+
+ @Description  Perform system level processing required after a device power
+                               transition
+
+ @Input                ui32DeviceIndex :
+ @Input                eNewPowerState :
+ @Input                eCurrentPowerState :
+
+ @Return       PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR SysDevicePostPowerState(IMG_UINT32                                ui32DeviceIndex,
                                                                         PVRSRV_DEV_POWER_STATE eNewPowerState,
                                                                         PVRSRV_DEV_POWER_STATE eCurrentPowerState)
@@ -932,14 +1244,33 @@ PVRSRV_ERROR SysDevicePostPowerState(IMG_UINT32                          ui32DeviceIndex,
                PVR_DPF((PVR_DBG_MESSAGE, "SysDevicePostPowerState: SGX Leaving state D3"));
                eError = EnableSGXClocksWrap(gpsSysData);
        }
-#else  
+#else  /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
        PVR_UNREFERENCED_PARAMETER(eCurrentPowerState);
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
 
        return eError;
 }
 
+#if defined(SYS_SUPPORTS_SGX_IDLE_CALLBACK)
+
+IMG_VOID SysSGXIdleTransition(IMG_BOOL bSGXIdle)
+{
+       PVR_DPF((PVR_DBG_MESSAGE, "SysSGXIdleTransition switch to %u", bSGXIdle));
+}
+
+#endif /* defined(SYS_SUPPORTS_SGX_IDLE_CALLBACK) */
+
+/*****************************************************************************
+ @Function        SysOEMFunction
+
+ @Description     marshalling function for custom OEM functions
+
+ @Input           ui32ID  - function ID
+ @Input           pvIn - in data
+ @Output          pvOut - out data
 
+ @Return        PVRSRV_ERROR
+*****************************************************************************/
 PVRSRV_ERROR SysOEMFunction (  IMG_UINT32      ui32ID,
                                                                IMG_VOID        *pvIn,
                                                                IMG_UINT32      ulInSize,
@@ -955,7 +1286,6 @@ PVRSRV_ERROR SysOEMFunction (      IMG_UINT32      ui32ID,
        if ((ui32ID == OEM_GET_EXT_FUNCS) &&
                (ulOutSize == sizeof(PVRSRV_DC_OEM_JTABLE)))
        {
-               
                PVRSRV_DC_OEM_JTABLE *psOEMJTable = (PVRSRV_DC_OEM_JTABLE*) pvOut;
                psOEMJTable->pfnOEMBridgeDispatch = &PVRSRV_BridgeDispatchKM;
                return PVRSRV_OK;
@@ -963,3 +1293,6 @@ PVRSRV_ERROR SysOEMFunction (      IMG_UINT32      ui32ID,
 
        return PVRSRV_ERROR_INVALID_PARAMS;
 }
+/******************************************************************************
+ End of file (sysconfig.c)
+******************************************************************************/
index 1a23743..64f3187 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          System Description Header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    This header provides system-specific declarations and macros
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined(__SOCCONFIG_H__)
 #define __SOCCONFIG_H__
 #define SYS_SGX_CLOCK_SPEED            304742400
 #endif
 
-#define SYS_SGX_HWRECOVERY_TIMEOUT_FREQ                (100)   
-#define SYS_SGX_PDS_TIMER_FREQ                         (1000)  
+#define SYS_SGX_HWRECOVERY_TIMEOUT_FREQ                (100)   // 10ms (100hz)
+#define SYS_SGX_PDS_TIMER_FREQ                         (1000)  // 1ms (1000hz)
 
+/* Allow the AP latency to be overridden in the build config */
 #if !defined(SYS_SGX_ACTIVE_POWER_LATENCY_MS)
 #define SYS_SGX_ACTIVE_POWER_LATENCY_MS                (2)
 #endif
 
 
 #define SYS_OMAP4430_SGX_REGS_SYS_PHYS_BASE  0x56000000
-
 #define SYS_OMAP4430_SGX_REGS_SIZE           0xFFFF
 
-#define SYS_OMAP4430_SGX_IRQ                            53 
+#define SYS_OMAP4430_SGX_IRQ                            53 /* OMAP4 IRQ's are offset by 32 */
+
+#define SYS_OMAP4430_DSS_REGS_SYS_PHYS_BASE  0x58000000
+#define SYS_OMAP4430_DSS_REGS_SIZE           0x7000
+
+#define SYS_OMAP4430_DSS_HDMI_INTERRUPT_STATUS_REG 0x6028
+#define SYS_OMAP4430_DSS_HDMI_INTERRUPT_ENABLE_REG 0x602c
+
+#define SYS_OMAP4430_DSS_HDMI_INTERRUPT_VSYNC_ENABLE_MASK 0x10000
+#define SYS_OMAP4430_DSS_HDMI_INTERRUPT_VSYNC_STATUS_MASK 0x10000
+
+#define SYS_OMAP4430_DSS_LCD_INTERRUPT_STATUS_REG 0x1018
+#define SYS_OMAP4430_DSS_LCD_INTERRUPT_ENABLE_REG 0x101c
+
+#define SYS_OMAP4430_DSS_LCD_INTERRUPT_VSYNC_ENABLE_MASK 0x40002
+#define SYS_OMAP4430_DSS_LCD_INTERRUPT_VSYNC_STATUS_MASK 0x40002
+
 
 #define SYS_OMAP4430_GP11TIMER_ENABLE_SYS_PHYS_BASE    0x48088038
 #define SYS_OMAP4430_GP11TIMER_REGS_SYS_PHYS_BASE      0x4808803C
 #define SYS_OMAP4430_GP11TIMER_TSICR_SYS_PHYS_BASE     0x48088054
 
+/* Interrupt bits */
+#define DEVICE_SGX_INTERRUPT           (1<<0)
+#define DEVICE_MSVDX_INTERRUPT         (1<<1)
+#define DEVICE_DISP_INTERRUPT          (1<<2)
+
 #if defined(__linux__)
+/*
+ * Recent OMAP4 kernels register SGX as platform device "omap_gpu".
+ * This device must be used with the Linux power management calls
+ * in sysutils_linux.c, in order for SGX to be powered on.
+ */
+#if defined(PVR_LDM_PLATFORM_PRE_REGISTERED_DEV)
+#define        SYS_SGX_DEV_NAME        PVR_LDM_PLATFORM_PRE_REGISTERED_DEV
+#else
 #define        SYS_SGX_DEV_NAME        "omap_gpu"
-#endif 
+#endif /* defined(PVR_LDM_PLATFORM_PRE_REGISTERED_DEV) */
+#endif /* defined(__linux__) */
 
+/*****************************************************************************
+ * system specific data structures
+ *****************************************************************************/
  
-#endif 
+#endif /* __SYSCONFIG_H__ */
index b6d3f5a..70ae148 100644 (file)
@@ -1,33 +1,56 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          System Description Header
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    This header provides system-specific declarations and macros
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined(__SYSINFO_H__)
 #define __SYSINFO_H__
 
+/*!< System specific poll/timeout details */
 #if defined(PVR_LINUX_USING_WORKQUEUES)
+/*
+ * The workqueue based 3rd party display driver may be blocked for up
+ * to 500ms waiting for a vsync when the screen goes blank, so we
+ * need to wait longer for the hardware if a flush of the swap chain is
+ * required.
+ */
 #define MAX_HW_TIME_US                         (1000000)
 #define WAIT_TRY_COUNT                         (20000)
 #else
@@ -36,6 +59,6 @@
 #endif
 
 
-#define SYS_DEVICE_COUNT 15 
+#define SYS_DEVICE_COUNT 15 /* SGX, DISPLAYCLASS (external), BUFFERCLASS (external) */
 
-#endif 
+#endif /* __SYSINFO_H__ */
index e07c51f..21e9675 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Local system definitions
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    This header provides local system declarations and macros
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #if !defined(__SYSLOCAL_H__)
 #define __SYSLOCAL_H__
 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26))
 #include <linux/semaphore.h>
 #include <linux/resource.h>
-#else 
+#else /* (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26)) */
 #include <asm/semaphore.h>
 #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,22))
 #include <asm/arch/resource.h>
-#endif 
-#endif 
+#endif /* (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,22)) */
+#endif /* (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26)) */
 
 
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,35))
 #if ((defined(DEBUG) || defined(TIMING)) && \
     (LINUX_VERSION_CODE == KERNEL_VERSION(2,6,34))) && \
     !defined(PVR_NO_OMAP_TIMER)
+/*
+ * We need to explicitly enable the GPTIMER11 clocks, or we'll get an
+ * abort when we try to access the timer registers.
+ */
 #define        PVR_OMAP4_TIMING_PRCM
 #endif
 
 #if !defined(PVR_NO_OMAP_TIMER)
 #define PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA
 #endif
-#endif 
+#endif /* defined(__linux__) */
 
 #if !defined(NO_HARDWARE) && \
-     defined(SYS_USING_INTERRUPTS) && \
-     defined(SGX540)
+     defined(SYS_USING_INTERRUPTS)
 #define SGX_OCP_REGS_ENABLED
 #endif
 
 #if defined(__linux__)
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,35)) && defined(SGX_OCP_REGS_ENABLED)
+#if defined(SGX_OCP_REGS_ENABLED)
 #define SGX_OCP_NO_INT_BYPASS
 #endif
 #endif
 extern "C" {
 #endif
 
+/*****************************************************************************
+ * system specific data structures
+ *****************************************************************************/
  
+/*****************************************************************************
+ * system specific function prototypes
+ *****************************************************************************/
  
 IMG_VOID DisableSystemClocks(SYS_DATA *psSysData);
 PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData);
@@ -100,6 +125,10 @@ PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData);
 IMG_VOID DisableSGXClocks(SYS_DATA *psSysData);
 PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData);
 
+/*
+ * Various flags to indicate what has been initialised, and what
+ * has been temporarily deinitialised for power management purposes.
+ */
 #define SYS_SPECIFIC_DATA_ENABLE_SYSCLOCKS     0x00000001
 #define SYS_SPECIFIC_DATA_ENABLE_LISR          0x00000002
 #define SYS_SPECIFIC_DATA_ENABLE_MISR          0x00000004
@@ -114,9 +143,8 @@ PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData);
 #define        SYS_SPECIFIC_DATA_PM_DISABLE_SYSCLOCKS  0x00000400
 #define SYS_SPECIFIC_DATA_ENABLE_OCPREGS       0x00000800
 #define SYS_SPECIFIC_DATA_ENABLE_PM_RUNTIME    0x00001000
-#if defined(SGX_OCP_REGS_ENABLED) && defined(SGX_OCP_NO_INT_BYPASS)
 #define SYS_SPECIFIC_DATA_IRQ_ENABLED          0x00002000
-#endif
+#define SYS_SPECIFIC_DATA_DVFS_INIT                    0x00004000
 
 #define        SYS_SPECIFIC_DATA_SET(psSysSpecData, flag) ((IMG_VOID)((psSysSpecData)->ui32SysSpecificData |= (flag)))
 
@@ -156,7 +184,10 @@ typedef struct _SYS_SPECIFIC_DATA_TAG_
 #if defined(PVR_OMAP_USE_DM_TIMER_API)
        struct omap_dm_timer *psGPTimer;
 #endif
-#endif 
+       IMG_UINT32 ui32SGXFreqListSize;
+       IMG_UINT32 *pui32SGXFreqList;
+       IMG_UINT32 ui32SGXFreqListIndex;
+#endif /* defined(__linux__) */
 } SYS_SPECIFIC_DATA;
 
 extern SYS_SPECIFIC_DATA *gpsSysSpecificData;
@@ -179,7 +210,10 @@ IMG_VOID UnwrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData);
 PVRSRV_ERROR SysPMRuntimeRegister(void);
 PVRSRV_ERROR SysPMRuntimeUnregister(void);
 
-#else 
+PVRSRV_ERROR SysDvfsInitialize(SYS_SPECIFIC_DATA *psSysSpecificData);
+PVRSRV_ERROR SysDvfsDeinitialize(SYS_SPECIFIC_DATA *psSysSpecificData);
+
+#else /* defined(__linux__) */
 
 #ifdef INLINE_IS_PRAGMA
 #pragma inline(SysPMRuntimeRegister)
@@ -197,12 +231,28 @@ static INLINE PVRSRV_ERROR SysPMRuntimeUnregister(void)
        return PVRSRV_OK;
 }
 
-#endif 
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(SysDvfsInitialize)
+#endif
+static INLINE PVRSRV_ERROR SysDvfsInitialize(void)
+{
+       return PVRSRV_OK;
+}
+
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(SysDvfsDeinitialize)
+#endif
+static INLINE PVRSRV_ERROR SysDvfsDeinitialize(void)
+{
+       return PVRSRV_OK;
+}
+
+#endif /* defined(__linux__) */
 
 #if defined(__cplusplus)
 }
 #endif
 
-#endif 
+#endif /* __SYSLOCAL_H__ */
 
 
index 8736fcc..27b2df6 100644 (file)
@@ -1,30 +1,49 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Shared (User/kernel) and System dependent utilities
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provides system-specific functions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+/* Pull in the correct system dependent sysutils source */
 
 #if defined(__linux__)
 #include "sysutils_linux.c"
 #endif
 
+
index 517cd0b..ebc4b05 100644 (file)
@@ -1,34 +1,50 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          System dependent utilities
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provides system-specific functions
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #include <linux/version.h>
 #include <linux/clk.h>
 #include <linux/err.h>
 #include <linux/hardirq.h>
 #include <linux/mutex.h>
+#include <linux/slab.h>
 
 #include "sgxdefs.h"
 #include "services_headers.h"
 #include <linux/platform_device.h>
 #include <linux/pm_runtime.h>
 
+#if defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK)
+#include <linux/opp.h>
+#endif
+
+#if defined(SUPPORT_DRI_DRM_PLUGIN)
+#include <drm/drmP.h>
+#include <drm/drm.h>
+
+#include <linux/omap_gpu.h>
+
+#include "pvr_drm.h"
+#endif
+
 #define        ONE_MHZ 1000000
 #define        HZ_TO_MHZ(m) ((m) / ONE_MHZ)
 
@@ -101,6 +130,15 @@ IMG_VOID SysPowerLockUnwrap(IMG_VOID)
        PowerLockUnwrap(psSysData->pvSysSpecificData);
 }
 
+/*
+ * This function should be called to unwrap the Services power lock, prior
+ * to calling any function that might sleep.
+ * This function shouldn't be called prior to calling EnableSystemClocks
+ * or DisableSystemClocks, as those functions perform their own power lock
+ * unwrapping.
+ * If the function returns IMG_TRUE, UnwrapSystemPowerChange must be
+ * called to rewrap the power lock, prior to returning to Services.
+ */
 IMG_BOOL WrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData)
 {
        return IMG_TRUE;
@@ -110,51 +148,46 @@ IMG_VOID UnwrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData)
 {
 }
 
-static inline IMG_UINT32 scale_by_rate(IMG_UINT32 val, IMG_UINT32 rate1, IMG_UINT32 rate2)
-{
-       if (rate1 >= rate2)
-       {
-               return val * (rate1 / rate2);
-       }
-
-       return val / (rate2 / rate1);
-}
-
-static inline IMG_UINT32 scale_prop_to_SGX_clock(IMG_UINT32 val, IMG_UINT32 rate)
-{
-       return scale_by_rate(val, rate, SYS_SGX_CLOCK_SPEED);
-}
-
-static inline IMG_UINT32 scale_inv_prop_to_SGX_clock(IMG_UINT32 val, IMG_UINT32 rate)
-{
-       return scale_by_rate(val, SYS_SGX_CLOCK_SPEED, rate);
-}
-
+/*
+ * Return SGX timining information to caller.
+ */
 IMG_VOID SysGetSGXTimingInformation(SGX_TIMING_INFORMATION *psTimingInfo)
 {
-       IMG_UINT32 rate;
-
-       rate = SYS_SGX_CLOCK_SPEED;
 #if !defined(NO_HARDWARE)
        PVR_ASSERT(atomic_read(&gpsSysSpecificData->sSGXClocksEnabled) != 0);
 #endif
-       psTimingInfo->ui32CoreClockSpeed = rate;
-       psTimingInfo->ui32HWRecoveryFreq = scale_prop_to_SGX_clock(SYS_SGX_HWRECOVERY_TIMEOUT_FREQ, rate);
-       psTimingInfo->ui32uKernelFreq = scale_prop_to_SGX_clock(SYS_SGX_PDS_TIMER_FREQ, rate);
+#if defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK)
+       psTimingInfo->ui32CoreClockSpeed =
+               gpsSysSpecificData->pui32SGXFreqList[gpsSysSpecificData->ui32SGXFreqListIndex];
+#else /* defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK) */
+       psTimingInfo->ui32CoreClockSpeed = SYS_SGX_CLOCK_SPEED;
+#endif
+       psTimingInfo->ui32HWRecoveryFreq = SYS_SGX_HWRECOVERY_TIMEOUT_FREQ;
+       psTimingInfo->ui32uKernelFreq = SYS_SGX_PDS_TIMER_FREQ;
 #if defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
        psTimingInfo->bEnableActivePM = IMG_TRUE;
 #else
        psTimingInfo->bEnableActivePM = IMG_FALSE;
-#endif 
+#endif /* SUPPORT_ACTIVE_POWER_MANAGEMENT */
        psTimingInfo->ui32ActivePowManLatencyms = SYS_SGX_ACTIVE_POWER_LATENCY_MS;
 }
 
+/*!
+******************************************************************************
+
+ @Function  EnableSGXClocks
+
+ @Description Enable SGX clocks
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData)
 {
 #if !defined(NO_HARDWARE)
        SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
 
-       
+       /* SGX clocks already enabled? */
        if (atomic_read(&psSysSpecData->sSGXClocksEnabled) != 0)
        {
                return PVRSRV_OK;
@@ -163,8 +196,49 @@ PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData)
        PVR_DPF((PVR_DBG_MESSAGE, "EnableSGXClocks: Enabling SGX Clocks"));
 
 #if defined(LDM_PLATFORM) && !defined(PVR_DRI_DRM_NOT_PCI)
+#if defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK)
+       {
+               struct gpu_platform_data *pdata;
+               IMG_UINT32 max_freq_index;
+               int res;
+
+               pdata = (struct gpu_platform_data *)gpsPVRLDMDev->dev.platform_data;
+               max_freq_index = psSysSpecData->ui32SGXFreqListSize - 2;
+
+               /*
+                * Request maximum frequency from DVFS layer if not already set. DVFS may
+                * report busy if early in initialization, but all other errors are
+                * considered serious. Upon any error we proceed assuming our safe frequency
+                * value to be in use as indicated by the "unknown" index.
+                */
+               if (psSysSpecData->ui32SGXFreqListIndex != max_freq_index)
+               {
+                       PVR_ASSERT(pdata->device_scale != IMG_NULL);
+                       res = pdata->device_scale(&gpsPVRLDMDev->dev,
+                                                                         &gpsPVRLDMDev->dev,
+                                                                         psSysSpecData->pui32SGXFreqList[max_freq_index]);
+                       if (res == 0)
+                       {
+                               psSysSpecData->ui32SGXFreqListIndex = max_freq_index;
+                       }
+                       else if (res == -EBUSY)
+                       {
+                               PVR_DPF((PVR_DBG_WARNING, "EnableSGXClocks: Unable to scale SGX frequency (EBUSY)"));
+                               psSysSpecData->ui32SGXFreqListIndex = psSysSpecData->ui32SGXFreqListSize - 1;
+                       }
+                       else if (res < 0)
+                       {
+                               PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: Unable to scale SGX frequency (%d)", res));
+                               psSysSpecData->ui32SGXFreqListIndex = psSysSpecData->ui32SGXFreqListSize - 1;
+                       }
+               }
+       }
+#endif /* defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK) */
        {
-               
+               /*
+                * pm_runtime_get_sync returns 1 after the module has
+                * been reloaded.
+                */
                int res = pm_runtime_get_sync(&gpsPVRLDMDev->dev);
                if (res < 0)
                {
@@ -172,25 +246,36 @@ PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData)
                        return PVRSRV_ERROR_UNABLE_TO_ENABLE_CLOCK;
                }
        }
-#endif
+#endif /* defined(LDM_PLATFORM) && !defined(PVR_DRI_DRM_NOT_PCI) */
+
        SysEnableSGXInterrupts(psSysData);
 
-       
+       /* Indicate that the SGX clocks are enabled */
        atomic_set(&psSysSpecData->sSGXClocksEnabled, 1);
 
-#else  
+#else  /* !defined(NO_HARDWARE) */
        PVR_UNREFERENCED_PARAMETER(psSysData);
-#endif 
+#endif /* !defined(NO_HARDWARE) */
        return PVRSRV_OK;
 }
 
 
+/*!
+******************************************************************************
+
+ @Function  DisableSGXClocks
+
+ @Description Disable SGX clocks.
+
+ @Return   none
+
+******************************************************************************/
 IMG_VOID DisableSGXClocks(SYS_DATA *psSysData)
 {
 #if !defined(NO_HARDWARE)
        SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
 
-       
+       /* SGX clocks already disabled? */
        if (atomic_read(&psSysSpecData->sSGXClocksEnabled) == 0)
        {
                return;
@@ -208,24 +293,75 @@ IMG_VOID DisableSGXClocks(SYS_DATA *psSysData)
                        PVR_DPF((PVR_DBG_ERROR, "DisableSGXClocks: pm_runtime_put_sync failed (%d)", -res));
                }
        }
-#endif
+#if defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK)
+       {
+               struct gpu_platform_data *pdata;
+               int res;
+
+               pdata = (struct gpu_platform_data *)gpsPVRLDMDev->dev.platform_data;
+
+               /*
+                * Request minimum frequency (list index 0) from DVFS layer if not already
+                * set. DVFS may report busy if early in initialization, but all other errors
+                * are considered serious. Upon any error we proceed assuming our safe frequency
+                * value to be in use as indicated by the "unknown" index.
+                */
+               if (psSysSpecData->ui32SGXFreqListIndex != 0)
+               {
+                       PVR_ASSERT(pdata->device_scale != IMG_NULL);
+                       res = pdata->device_scale(&gpsPVRLDMDev->dev,
+                                                                         &gpsPVRLDMDev->dev,
+                                                                         psSysSpecData->pui32SGXFreqList[0]);
+                       if (res == 0)
+                       {
+                               psSysSpecData->ui32SGXFreqListIndex = 0;
+                       }
+                       else if (res == -EBUSY)
+                       {
+                               PVR_DPF((PVR_DBG_WARNING, "DisableSGXClocks: Unable to scale SGX frequency (EBUSY)"));
+                               psSysSpecData->ui32SGXFreqListIndex = psSysSpecData->ui32SGXFreqListSize - 1;
+                       }
+                       else if (res < 0)
+                       {
+                               PVR_DPF((PVR_DBG_ERROR, "DisableSGXClocks: Unable to scale SGX frequency (%d)", res));
+                               psSysSpecData->ui32SGXFreqListIndex = psSysSpecData->ui32SGXFreqListSize - 1;
+                       }
+               }
+       }
+#endif /* defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK) */
+#endif /* defined(LDM_PLATFORM) && !defined(PVR_DRI_DRM_NOT_PCI) */
 
-       
+       /* Indicate that the SGX clocks are disabled */
        atomic_set(&psSysSpecData->sSGXClocksEnabled, 0);
 
-#else  
+#else  /* !defined(NO_HARDWARE) */
        PVR_UNREFERENCED_PARAMETER(psSysData);
-#endif 
+#endif /* !defined(NO_HARDWARE) */
 }
 
 #if (defined(DEBUG) || defined(TIMING)) && !defined(PVR_NO_OMAP_TIMER)
 #if defined(PVR_OMAP_USE_DM_TIMER_API)
 #define        GPTIMER_TO_USE 11
+/*!
+******************************************************************************
+
+ @Function  AcquireGPTimer
+
+ @Description Acquire a GP timer
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
 {
        PVR_ASSERT(psSysSpecData->psGPTimer == NULL);
 
-       
+       /*
+        * This code could try requesting registers 9, 10, and 11,
+        * stopping at the first succesful request.  We'll stick with
+        * 11 for now, as it avoids having to hard code yet more
+        * physical addresses into the code.
+        */
        psSysSpecData->psGPTimer = omap_dm_timer_request_specific(GPTIMER_TO_USE);
        if (psSysSpecData->psGPTimer == NULL)
        {
@@ -234,26 +370,39 @@ static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
                return PVRSRV_ERROR_CLOCK_REQUEST_FAILED;
        }
 
-       
+       /* Set timer source to system clock */
        omap_dm_timer_set_source(psSysSpecData->psGPTimer, OMAP_TIMER_SRC_SYS_CLK);
        omap_dm_timer_enable(psSysSpecData->psGPTimer);
 
-       
+       /* Set autoreload, and start value of 0 */
        omap_dm_timer_set_load_start(psSysSpecData->psGPTimer, 1, 0);
 
        omap_dm_timer_start(psSysSpecData->psGPTimer);
 
-       
+       /*
+        * The DM timer API doesn't have a mechansim for obtaining the
+        * physical address of the counter register.
+        */
        psSysSpecData->sTimerRegPhysBase.uiAddr = SYS_OMAP4430_GP11TIMER_REGS_SYS_PHYS_BASE;
 
        return PVRSRV_OK;
 }
 
+/*!
+******************************************************************************
+
+ @Function  ReleaseGPTimer
+
+ @Description Release a GP timer
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
 {
        if (psSysSpecData->psGPTimer != NULL)
        {
-                       
+               /* Always returns 0 */  
                (void) omap_dm_timer_stop(psSysSpecData->psGPTimer);
 
                omap_dm_timer_disable(psSysSpecData->psGPTimer);
@@ -266,7 +415,17 @@ static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
        }
 
 }
-#else  
+#else  /* PVR_OMAP_USE_DM_TIMER_API */
+/*!
+******************************************************************************
+
+ @Function  AcquireGPTimer
+
+ @Description Acquire a GP timer
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
 {
 #if defined(PVR_OMAP4_TIMING_PRCM)
@@ -284,7 +443,7 @@ static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
        PVR_ASSERT(psSysSpecData->sTimerRegPhysBase.uiAddr == 0);
 
 #if defined(PVR_OMAP4_TIMING_PRCM)
-       
+       /* assert our dependence on the GPTIMER11 module */
        psCLK = clk_get(NULL, "gpt11_fck");
        if (IS_ERR(psCLK))
        {
@@ -335,9 +494,9 @@ static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
                PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't enable GPTIMER11 interface clock (%d)", res));
                goto ExitDisableGPT11FCK;
        }
-#endif 
+#endif /* defined(PVR_OMAP4_TIMING_PRCM) */
 
-       
+       /* Set the timer to non-posted mode */
        sTimerRegPhysBase.uiAddr = SYS_OMAP4430_GP11TIMER_TSICR_SYS_PHYS_BASE;
        pui32TimerEnable = OSMapPhysToLin(sTimerRegPhysBase,
                   4,
@@ -354,7 +513,7 @@ static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
        {
                PVR_TRACE(("Setting GPTIMER11 mode to posted (currently is non-posted)"));
 
-               
+               /* Set posted mode */
                *pui32TimerEnable |= 4;
        }
 
@@ -363,7 +522,7 @@ static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
                    PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
                    hTimerEnable);
 
-       
+       /* Enable the timer */
        sTimerRegPhysBase.uiAddr = SYS_OMAP4430_GP11TIMER_ENABLE_SYS_PHYS_BASE;
        pui32TimerEnable = OSMapPhysToLin(sTimerRegPhysBase,
                   4,
@@ -376,7 +535,7 @@ static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
                goto ExitDisableGPT11ICK;
        }
 
-       
+       /* Enable and set autoreload on overflow */
        *pui32TimerEnable = 3;
 
        OSUnMapPhysToLin(pui32TimerEnable,
@@ -396,12 +555,22 @@ ExitDisableGPT11ICK:
 ExitDisableGPT11FCK:
        clk_disable(psSysSpecData->psGPT11_FCK);
 ExitError:
-#endif 
+#endif /* defined(PVR_OMAP4_TIMING_PRCM) */
        eError = PVRSRV_ERROR_CLOCK_REQUEST_FAILED;
 Exit:
        return eError;
 }
 
+/*!
+******************************************************************************
+
+ @Function  ReleaseGPTimer
+
+ @Description Release a GP timer
+
+ @Return   PVRSRV_ERROR
+
+******************************************************************************/
 static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
 {
        IMG_HANDLE hTimerDisable;
@@ -412,7 +581,7 @@ static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
                return;
        }
 
-       
+       /* Disable the timer */
        pui32TimerDisable = OSMapPhysToLin(psSysSpecData->sTimerRegPhysBase,
                                4,
                                PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
@@ -438,10 +607,10 @@ static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
        clk_disable(psSysSpecData->psGPT11_ICK);
 
        clk_disable(psSysSpecData->psGPT11_FCK);
-#endif 
+#endif /* defined(PVR_OMAP4_TIMING_PRCM) */
 }
-#endif 
-#else  
+#endif /* PVR_OMAP_USE_DM_TIMER_API */
+#else  /* (DEBUG || TIMING) && !PVR_NO_OMAP_TIMER */
 static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
 {
        PVR_UNREFERENCED_PARAMETER(psSysSpecData);
@@ -452,8 +621,18 @@ static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
 {
        PVR_UNREFERENCED_PARAMETER(psSysSpecData);
 }
-#endif 
+#endif /* (DEBUG || TIMING) && !PVR_NO_OMAP_TIMER */
+
+/*!
+******************************************************************************
+
+ @Function  EnableSystemClocks
+
+ @Description Setup up the clocks for the graphics device to work.
+
+ @Return   PVRSRV_ERROR
 
+******************************************************************************/
 PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
 {
        SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
@@ -472,13 +651,27 @@ PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
        return AcquireGPTimer(psSysSpecData);
 }
 
+/*!
+******************************************************************************
+
+ @Function  DisableSystemClocks
+
+ @Description Disable the graphics clocks.
+
+ @Return  none
+
+******************************************************************************/
 IMG_VOID DisableSystemClocks(SYS_DATA *psSysData)
 {
        SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
 
        PVR_TRACE(("DisableSystemClocks: Disabling System Clocks"));
 
-       
+       /*
+        * Always disable the SGX clocks when the system clocks are disabled.
+        * This saves having to make an explicit call to DisableSGXClocks if
+        * active power management is enabled.
+        */
        DisableSGXClocks(psSysData);
 
        ReleaseGPTimer(psSysSpecData);
@@ -499,3 +692,158 @@ PVRSRV_ERROR SysPMRuntimeUnregister(void)
 #endif
        return PVRSRV_OK;
 }
+
+PVRSRV_ERROR SysDvfsInitialize(SYS_SPECIFIC_DATA *psSysSpecificData)
+{
+#if !defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK)
+       PVR_UNREFERENCED_PARAMETER(psSysSpecificData);
+#else /* !defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK) */
+       IMG_UINT32 i, *freq_list;
+       IMG_INT32 opp_count;
+       unsigned long freq;
+       struct opp *opp;
+
+       /*
+        * We query and store the list of SGX frequencies just this once under the
+        * assumption that they are unchanging, e.g. no disabling of high frequency
+        * option for thermal management. This is currently valid for 4430 and 4460.
+        */
+       rcu_read_lock();
+       opp_count = opp_get_opp_count(&gpsPVRLDMDev->dev);
+       if (opp_count < 1)
+       {
+               rcu_read_unlock();
+               PVR_DPF((PVR_DBG_ERROR, "SysDvfsInitialize: Could not retrieve opp count"));
+               return PVRSRV_ERROR_NOT_SUPPORTED;
+       }
+
+       /*
+        * Allocate the frequency list with a slot for each available frequency plus
+        * one additional slot to hold a designated frequency value to assume when in
+        * an unknown frequency state.
+        */
+       freq_list = kmalloc((opp_count + 1) * sizeof(IMG_UINT32), GFP_ATOMIC);
+       if (!freq_list)
+       {
+               rcu_read_unlock();
+               PVR_DPF((PVR_DBG_ERROR, "SysDvfsInitialize: Could not allocate frequency list"));
+               return PVRSRV_ERROR_OUT_OF_MEMORY;
+       }
+
+       /*
+        * Fill in frequency list from lowest to highest then finally the "unknown"
+        * frequency value. We use the highest available frequency as our assumed value
+        * when in an unknown state, because it is safer for APM and hardware recovery
+        * timers to be longer than intended rather than shorter.
+        */
+       freq = 0;
+       for (i = 0; i < opp_count; i++)
+       {
+               opp = opp_find_freq_ceil(&gpsPVRLDMDev->dev, &freq);
+               if (IS_ERR_OR_NULL(opp))
+               {
+                       rcu_read_unlock();
+                       PVR_DPF((PVR_DBG_ERROR, "SysDvfsInitialize: Could not retrieve opp level %d", i));
+                       kfree(freq_list);
+                       return PVRSRV_ERROR_NOT_SUPPORTED;
+               }
+               freq_list[i] = (IMG_UINT32)freq;
+               freq++;
+       }
+       rcu_read_unlock();
+       freq_list[opp_count] = freq_list[opp_count - 1];
+
+       psSysSpecificData->ui32SGXFreqListSize = opp_count + 1;
+       psSysSpecificData->pui32SGXFreqList = freq_list;
+
+       /* Start in unknown state - no frequency request to DVFS yet made */
+       psSysSpecificData->ui32SGXFreqListIndex = opp_count;
+#endif /* !defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK) */
+
+       return PVRSRV_OK;
+}
+
+PVRSRV_ERROR SysDvfsDeinitialize(SYS_SPECIFIC_DATA *psSysSpecificData)
+{
+#if !defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK)
+       PVR_UNREFERENCED_PARAMETER(psSysSpecificData);
+#else /* !defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK) */
+       /*
+        * We assume this function is only called if SysDvfsInitialize() was
+        * completed successfully before.
+        *
+        * The DVFS interface does not allow us to actually unregister as a
+        * user of SGX, so we do the next best thing which is to lower our
+        * required frequency to the minimum if not already set. DVFS may
+        * report busy if early in initialization, but all other errors are
+        * considered serious.
+        */
+       if (psSysSpecificData->ui32SGXFreqListIndex != 0)
+       {
+               struct gpu_platform_data *pdata;
+               IMG_INT32 res;
+
+               pdata = (struct gpu_platform_data *)gpsPVRLDMDev->dev.platform_data;
+
+               PVR_ASSERT(pdata->device_scale != IMG_NULL);
+               res = pdata->device_scale(&gpsPVRLDMDev->dev,
+                                                                 &gpsPVRLDMDev->dev,
+                                                                 psSysSpecificData->pui32SGXFreqList[0]);
+               if (res == -EBUSY)
+               {
+                       PVR_DPF((PVR_DBG_WARNING, "SysDvfsDeinitialize: Unable to scale SGX frequency (EBUSY)"));
+               }
+               else if (res < 0)
+               {
+                       PVR_DPF((PVR_DBG_ERROR, "SysDvfsDeinitialize: Unable to scale SGX frequency (%d)", res));
+               }
+
+               psSysSpecificData->ui32SGXFreqListIndex = 0;
+       }
+
+       kfree(psSysSpecificData->pui32SGXFreqList);
+       psSysSpecificData->pui32SGXFreqList = 0;
+       psSysSpecificData->ui32SGXFreqListSize = 0;
+#endif /* !defined(SYS_OMAP4_HAS_DVFS_FRAMEWORK) */
+
+       return PVRSRV_OK;
+}
+
+#if defined(SUPPORT_DRI_DRM_PLUGIN)
+static struct omap_gpu_plugin sOMAPGPUPlugin;
+
+#define        SYS_DRM_SET_PLUGIN_FIELD(d, s, f) (d)->f = (s)->f
+int
+SysDRMRegisterPlugin(PVRSRV_DRM_PLUGIN *psDRMPlugin)
+{
+       int iRes;
+
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, name);
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, open);
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, load);
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, unload);
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, release);
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, mmap);
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, ioctls);
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, num_ioctls);
+       SYS_DRM_SET_PLUGIN_FIELD(&sOMAPGPUPlugin, psDRMPlugin, ioctl_start);
+
+       iRes = omap_gpu_register_plugin(&sOMAPGPUPlugin);
+       if (iRes != 0)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: omap_gpu_register_plugin failed (%d)", __FUNCTION__, iRes));
+       }
+
+       return iRes;
+}
+
+void
+SysDRMUnregisterPlugin(PVRSRV_DRM_PLUGIN *psDRMPlugin)
+{
+       int iRes = omap_gpu_unregister_plugin(&sOMAPGPUPlugin);
+       if (iRes != 0)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: omap_gpu_unregister_plugin failed (%d)", __FUNCTION__, iRes));
+       }
+}
+#endif
index 2599570..0d23f62 100644 (file)
@@ -471,6 +471,7 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                OSReservePhys(TimerRegPhysBase,
                                  4,
                                  PVRSRV_HAP_MULTI_PROCESS|PVRSRV_HAP_UNCACHED,
+                                 IMG_NULL,
                                  (IMG_VOID **)&gpsSysData->pvSOCTimerRegisterKM,
                                  &gpsSysData->hSOCTimerRegisterOSMemHandle);
        }
index 206f7fa..c8eea1e 100644 (file)
@@ -1,6 +1,6 @@
 /**********************************************************************
  *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
+ * Copyright (C) Imagination Technologies Ltd. All rights reserved.
  * 
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
index 7dcb359..5438174 100644 (file)
@@ -1,6 +1,6 @@
 /**********************************************************************
  *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
+ * Copyright (C) Imagination Technologies Ltd. All rights reserved.
  * 
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
  *
  ******************************************************************************/
 
+#include "sysconfig.h"
 #include "services_headers.h"
 #include "kerneldisplay.h"
 #include "oemfuncs.h"
 #include "sgxinfo.h"
 #include "sgxinfokm.h"
 #include "syslocal.h"
-#include "sysconfig.h"
 
 #include "ocpdefs.h"
 
-#if !defined(NO_HARDWARE) && \
-     defined(SYS_USING_INTERRUPTS) && \
-     defined(SGX530) && (SGX_CORE_REV == 125)
-#define SGX_OCP_REGS_ENABLED
-#endif
-
 SYS_DATA* gpsSysData = (SYS_DATA*)IMG_NULL;
 SYS_DATA  gsSysData;
 
@@ -52,10 +46,14 @@ static PVRSRV_DEVICE_NODE *gpsSGXDevNode;
 
 #define DEVICE_SGX_INTERRUPT (1 << 0)
 
-#if defined(NO_HARDWARE)
+#if defined(NO_HARDWARE) || defined(SGX_OCP_REGS_ENABLED)
 static IMG_CPU_VIRTADDR gsSGXRegsCPUVAddr;
 #endif
 
+#if defined(PVR_LINUX_DYNAMIC_SGX_RESOURCE_INFO)
+extern struct platform_device *gpsPVRLDMDev;
+#endif
+
 IMG_UINT32 PVRSRV_BridgeDispatchKM(IMG_UINT32  Ioctl,
                                                                   IMG_BYTE             *pInBuf,
                                                                   IMG_UINT32   InBufLen,
@@ -63,115 +61,21 @@ IMG_UINT32 PVRSRV_BridgeDispatchKM(IMG_UINT32      Ioctl,
                                                                   IMG_UINT32   OutBufLen,
                                                                   IMG_UINT32   *pdwBytesTransferred);
 
-#if defined(DEBUG) && defined(DUMP_OMAP34xx_CLOCKS) && defined(__linux__)
-
-#pragma GCC diagnostic ignored "-Wstrict-prototypes"
-#include <mach/clock.h>
-
-#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,29))
-#include <../mach-omap2/clock_34xx.h>
-#define ONCHIP_CLKS onchip_clks
-#else
-#include <../mach-omap2/clock34xx.h>
-#define ONCHIP_CLKS onchip_34xx_clks
-#endif
-
-static void omap3_clk_recalc(struct clk *clk) {}
-static void omap3_followparent_recalc(struct clk *clk) {}
-static void omap3_propagate_rate(struct clk *clk) {}
-static void omap3_table_recalc(struct clk *clk) {}
-static long omap3_round_to_table_rate(struct clk *clk, unsigned long rate) { return 0; }
-static int omap3_select_table_rate(struct clk *clk, unsigned long rate) { return 0; }
-
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,29))
-static void omap3_dpll_recalc(struct clk *clk, unsigned long parent_rate,
-                                                         u8 rate_storage) {}
-static void omap3_clkoutx2_recalc(struct clk *clk, unsigned long parent_rate,
-                                                                 u8 rate_storage) {}
-static void omap3_dpll_allow_idle(struct clk *clk) {}
-static void omap3_dpll_deny_idle(struct clk *clk) {}
-static u32 omap3_dpll_autoidle_read(struct clk *clk) { return 0; }
-static int omap3_noncore_dpll_enable(struct clk *clk) { return 0; }
-static void omap3_noncore_dpll_disable(struct clk *clk) {}
-static int omap3_noncore_dpll_set_rate(struct clk *clk, unsigned long rate) { return 0; }
-static int omap3_core_dpll_m2_set_rate(struct clk *clk, unsigned long rate) { return 0; }
-void followparent_recalc(struct clk *clk, unsigned long new_parent_rate,
-                                                               u8 rate_storage) {}
-long omap2_dpll_round_rate(struct clk *clk, unsigned long target_rate) { return 0; }
-void omap2_clksel_recalc(struct clk *clk, unsigned long new_parent_rate,
-                                                               u8 rate_storage) {}
-long omap2_clksel_round_rate(struct clk *clk, unsigned long target_rate) { return 0; }
-int omap2_clksel_set_rate(struct clk *clk, unsigned long rate) { return 0; }
-void omap2_fixed_divisor_recalc(struct clk *clk, unsigned long new_parent_rate,
-                                                                          u8 rate_storage) {}
-void omap2_init_clksel_parent(struct clk *clk) {}
-#endif
-
-static void dump_omap34xx_clocks(void)
-{
-       struct clk **c;
-#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,29))
-       struct vdd_prcm_config *t1 = vdd1_rate_table;
-       struct vdd_prcm_config *t2 = vdd2_rate_table;
-
-       t1 = t1;
-       t2 = t2;
-#else
-       
-       omap3_dpll_allow_idle(0);
-       omap3_dpll_deny_idle(0);
-       omap3_dpll_autoidle_read(0);
-       omap3_clk_recalc(0);
-       omap3_followparent_recalc(0);
-       omap3_propagate_rate(0);
-       omap3_table_recalc(0);
-       omap3_round_to_table_rate(0, 0);
-       omap3_select_table_rate(0, 0);
-#endif
-
-       for(c = ONCHIP_CLKS; c < ONCHIP_CLKS + ARRAY_SIZE(ONCHIP_CLKS); c++)
-       {
-               struct clk *cp = *c, *copy;
-               unsigned long rate;
-               copy = clk_get(NULL, cp->name);
-               if(!copy)
-                       continue;
-               rate = clk_get_rate(copy);
-               if (rate < 1000000)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "%s: clock %s is %lu KHz (%lu Hz)", __func__, cp->name, rate/1000, rate));
-               }
-               else
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "%s: clock %s is %lu MHz (%lu Hz)", __func__, cp->name, rate/1000000, rate));
-               }
-       }
-}
-
-#else  
-
-static INLINE void dump_omap34xx_clocks(void) {}
-
-#endif 
-
 #if defined(SGX_OCP_REGS_ENABLED)
 
-#define SYS_TI81xx_OCP_REGS_SYS_PHYS_BASE              (SYS_TI81xx_SGX_REGS_SYS_PHYS_BASE + EUR_CR_OCP_REVISION)
-#define SYS_TI81xx_OCP_REGS_SIZE                               0x110
-
 static IMG_CPU_VIRTADDR gpvOCPRegsLinAddr;
 
 static PVRSRV_ERROR EnableSGXClocksWrap(SYS_DATA *psSysData)
 {
        PVRSRV_ERROR eError = EnableSGXClocks(psSysData);
 
+#if !defined(SGX_OCP_NO_INT_BYPASS)
        if(eError == PVRSRV_OK)
        {
-               OSWriteHWReg(gpvOCPRegsLinAddr,
-                                        EUR_CR_OCP_DEBUG_CONFIG - EUR_CR_OCP_REVISION,
-                                        EUR_CR_OCP_DEBUG_CONFIG_THALIA_INT_BYPASS_MASK);
+               OSWriteHWReg(gpvOCPRegsLinAddr, EUR_CR_OCP_SYSCONFIG, 0x14);
+               OSWriteHWReg(gpvOCPRegsLinAddr, EUR_CR_OCP_DEBUG_CONFIG, EUR_CR_OCP_DEBUG_CONFIG_THALIA_INT_BYPASS_MASK);
        }
-
+#endif
        return eError;
 }
 
@@ -192,7 +96,11 @@ static INLINE PVRSRV_ERROR EnableSystemClocksWrap(SYS_DATA *psSysData)
        if(eError == PVRSRV_OK)
        {
                
-               EnableSGXClocksWrap(psSysData);
+               eError = EnableSGXClocksWrap(psSysData);
+               if (eError != PVRSRV_OK)
+               {
+                       DisableSystemClocks(psSysData);
+               }
        }
 #endif
 
@@ -204,6 +112,11 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
 #if defined(NO_HARDWARE)
        PVRSRV_ERROR eError;
        IMG_CPU_PHYADDR sCpuPAddr;
+#else
+#if defined(PVR_LINUX_DYNAMIC_SGX_RESOURCE_INFO)
+       struct resource *dev_res;
+       int dev_irq;
+#endif
 #endif
 
        PVR_UNREFERENCED_PARAMETER(psSysData);
@@ -214,7 +127,9 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
 #if defined(NO_HARDWARE)
        
        
-       eError = OSBaseAllocContigMemory(SYS_TI81xx_SGX_REGS_SIZE, 
+       gsSGXDeviceMap.ui32RegsSize = SYS_TI81xx_SGX_REGS_SIZE;
+
+       eError = OSBaseAllocContigMemory(gsSGXDeviceMap.ui32RegsSize,
                                                                         &gsSGXRegsCPUVAddr,
                                                                         &sCpuPAddr);
        if(eError != PVRSRV_OK)
@@ -223,7 +138,6 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
        }
        gsSGXDeviceMap.sRegsCpuPBase = sCpuPAddr;
        gsSGXDeviceMap.sRegsSysPBase = SysCpuPAddrToSysPAddr(gsSGXDeviceMap.sRegsCpuPBase);
-       gsSGXDeviceMap.ui32RegsSize = SYS_TI81xx_SGX_REGS_SIZE;
 #if defined(__linux__)
        
        gsSGXDeviceMap.pvRegsCpuVBase = gsSGXRegsCPUVAddr;
@@ -232,7 +146,7 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
        gsSGXDeviceMap.pvRegsCpuVBase = IMG_NULL;
 #endif
 
-       OSMemSet(gsSGXRegsCPUVAddr, 0, SYS_TI81xx_SGX_REGS_SIZE);
+       OSMemSet(gsSGXRegsCPUVAddr, 0, gsSGXDeviceMap.ui32RegsSize);
 
        
 
@@ -240,13 +154,56 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
        gsSGXDeviceMap.ui32IRQ = 0;
 
 #else 
+#if defined(PVR_LINUX_DYNAMIC_SGX_RESOURCE_INFO)
+       
+       dev_res = platform_get_resource(gpsPVRLDMDev, IORESOURCE_MEM, 0);
+       if (dev_res == NULL)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: platform_get_resource failed", __FUNCTION__));
+               return PVRSRV_ERROR_INVALID_DEVICE;
+       }
+
+       dev_irq = platform_get_irq(gpsPVRLDMDev, 0);
+       if (dev_irq < 0)
+       {
+               PVR_DPF((PVR_DBG_ERROR, "%s: platform_get_irq failed (%d)", __FUNCTION__, -dev_irq));
+               return PVRSRV_ERROR_INVALID_DEVICE;
+       }
+       
+       gsSGXDeviceMap.sRegsSysPBase.uiAddr = dev_res->start;
+       gsSGXDeviceMap.sRegsCpuPBase =
+               SysSysPAddrToCpuPAddr(gsSGXDeviceMap.sRegsSysPBase);
+       PVR_TRACE(("SGX register base: 0x%lx", (unsigned long)gsSGXDeviceMap.sRegsCpuPBase.uiAddr));
 
+       gsSGXDeviceMap.ui32RegsSize = (unsigned int)(dev_res->end - dev_res->start);
+       PVR_TRACE(("SGX register size: %d",gsSGXDeviceMap.ui32RegsSize));
+
+       gsSGXDeviceMap.ui32IRQ = dev_irq;
+       PVR_TRACE(("SGX IRQ: %d", gsSGXDeviceMap.ui32IRQ));
+#else  
        gsSGXDeviceMap.sRegsSysPBase.uiAddr = SYS_TI81xx_SGX_REGS_SYS_PHYS_BASE;
        gsSGXDeviceMap.sRegsCpuPBase = SysSysPAddrToCpuPAddr(gsSGXDeviceMap.sRegsSysPBase);
        gsSGXDeviceMap.ui32RegsSize = SYS_TI81xx_SGX_REGS_SIZE;
 
        gsSGXDeviceMap.ui32IRQ = SYS_TI81xx_SGX_IRQ;
 
+#endif 
+#if defined(SGX_OCP_REGS_ENABLED)
+       gsSGXRegsCPUVAddr = OSMapPhysToLin(gsSGXDeviceMap.sRegsCpuPBase,
+       gsSGXDeviceMap.ui32RegsSize,
+                                                                                        PVRSRV_HAP_UNCACHED|PVRSRV_HAP_KERNEL_ONLY,
+                                                                                        IMG_NULL);
+
+       if (gsSGXRegsCPUVAddr == IMG_NULL)
+       {
+               PVR_DPF((PVR_DBG_ERROR,"SysLocateDevices: Failed to map SGX registers"));
+               return PVRSRV_ERROR_BAD_MAPPING;
+       }
+
+       
+       gsSGXDeviceMap.pvRegsCpuVBase = gsSGXRegsCPUVAddr;
+       gpvOCPRegsLinAddr = gsSGXRegsCPUVAddr;
+#endif
 #endif 
 
 #if defined(PDUMP)
@@ -264,7 +221,7 @@ static PVRSRV_ERROR SysLocateDevices(SYS_DATA *psSysData)
 }
 
 
-IMG_CHAR *SysCreateVersionString(IMG_CPU_PHYADDR sRegRegion)
+static IMG_CHAR *SysCreateVersionString(void)
 {
        static IMG_CHAR aszVersionString[100];
        SYS_DATA        *psSysData;
@@ -273,7 +230,7 @@ IMG_CHAR *SysCreateVersionString(IMG_CPU_PHYADDR sRegRegion)
 #if !defined(NO_HARDWARE)
        IMG_VOID        *pvRegsLinAddr;
 
-       pvRegsLinAddr = OSMapPhysToLin(sRegRegion,
+       pvRegsLinAddr = OSMapPhysToLin(gsSGXDeviceMap.sRegsCpuPBase,
                                                                   SYS_TI81xx_SGX_REGS_SIZE,
                                                                   PVRSRV_HAP_UNCACHED|PVRSRV_HAP_KERNEL_ONLY,
                                                                   IMG_NULL);
@@ -321,7 +278,9 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
        IMG_UINT32                      i;
        PVRSRV_ERROR            eError;
        PVRSRV_DEVICE_NODE      *psDeviceNode;
+#if !defined(PVR_NO_OMAP_TIMER)
        IMG_CPU_PHYADDR         TimerRegPhysBase;
+#endif
 #if !defined(SGX_DYNAMIC_TIMING_INFO)
        SGX_TIMING_INFORMATION* psTimingInfo;
 #endif
@@ -364,27 +323,13 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                return eError;
        }
 
-       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_REGS_SYS_PHYS_BASE;
-       gpsSysData->pvSOCTimerRegisterKM = IMG_NULL;
-       gpsSysData->hSOCTimerRegisterOSMemHandle = 0;
-       OSReservePhys(TimerRegPhysBase,
-                                 4,
-                                 PVRSRV_HAP_MULTI_PROCESS|PVRSRV_HAP_UNCACHED,
-                                 (IMG_VOID **)&gpsSysData->pvSOCTimerRegisterKM,
-                                 &gpsSysData->hSOCTimerRegisterOSMemHandle);
-
 #if !defined(SGX_DYNAMIC_TIMING_INFO)
        
        psTimingInfo = &gsSGXDeviceMap.sTimingInfo;
-       if(cpu_is_ti816x())
-       {
-               psTimingInfo->ui32CoreClockSpeed = SYS_389x_SGX_CLOCK_SPEED;
-       }
-       else
-       {
-               psTimingInfo->ui32CoreClockSpeed = SYS_387x_SGX_CLOCK_SPEED;
-       }
-
+if(cpu_is_ti816x())
+       psTimingInfo->ui32CoreClockSpeed = SYS_389x_SGX_CLOCK_SPEED;
+else
+       psTimingInfo->ui32CoreClockSpeed = SYS_387x_SGX_CLOCK_SPEED;
        psTimingInfo->ui32HWRecoveryFreq = SYS_SGX_HWRECOVERY_TIMEOUT_FREQ; 
 #if defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
        psTimingInfo->bEnableActivePM = IMG_TRUE;
@@ -412,28 +357,17 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
                return eError;
        }
        SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_LOCATEDEV);
-
-#if defined(SGX_OCP_REGS_ENABLED)
+#if 0
+       eError = SysPMRuntimeRegister();
+       if (eError != PVRSRV_OK)
        {
-               IMG_SYS_PHYADDR sOCPRegsSysPBase;
-               IMG_CPU_PHYADDR sOCPRegsCpuPBase;
-
-               sOCPRegsSysPBase.uiAddr = SYS_TI81xx_OCP_REGS_SYS_PHYS_BASE;
-               sOCPRegsCpuPBase                = SysSysPAddrToCpuPAddr(sOCPRegsSysPBase);
-
-               gpvOCPRegsLinAddr               = OSMapPhysToLin(sOCPRegsCpuPBase,
-                                                                                                SYS_TI81xx_OCP_REGS_SIZE,
-                                                                                                PVRSRV_HAP_UNCACHED|PVRSRV_HAP_KERNEL_ONLY,
-                                                                                                IMG_NULL);
-
-               if (gpvOCPRegsLinAddr == IMG_NULL)
-               {
-                       PVR_DPF((PVR_DBG_ERROR,"SysInitialise: Failed to map OCP registers"));
-                       return PVRSRV_ERROR_BAD_MAPPING;
-               }
+               PVR_DPF((PVR_DBG_ERROR,"SysInitialise: Failed to register with OSPM!"));
+               (IMG_VOID)SysDeinitialise(gpsSysData);
+               gpsSysData = IMG_NULL;
+               return eError;
        }
+       SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_PM_RUNTIME);
 #endif
-
        
 
 
@@ -512,8 +446,6 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
        }
 #endif 
 
-       dump_omap34xx_clocks();
-
        eError = PVRSRVInitialiseDevice(gui32SGXDeviceID);
        if (eError != PVRSRV_OK)
        {
@@ -529,6 +461,25 @@ PVRSRV_ERROR SysInitialise(IMG_VOID)
        DisableSGXClocks(gpsSysData);
 #endif 
 
+#if !defined(PVR_NO_OMAP_TIMER)
+#if defined(PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA)
+       TimerRegPhysBase = gsSysSpecificData.sTimerRegPhysBase;
+#else
+       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_REGS_SYS_PHYS_BASE;
+#endif
+       gpsSysData->pvSOCTimerRegisterKM = IMG_NULL;
+       gpsSysData->hSOCTimerRegisterOSMemHandle = 0;
+       if (TimerRegPhysBase.uiAddr != 0)
+       {
+               OSReservePhys(TimerRegPhysBase,
+                                 4,
+                                 PVRSRV_HAP_MULTI_PROCESS|PVRSRV_HAP_UNCACHED,
+                                 IMG_NULL,
+                                 (IMG_VOID **)&gpsSysData->pvSOCTimerRegisterKM,
+                                 &gpsSysData->hSOCTimerRegisterOSMemHandle);
+       }
+#endif 
+
        return PVRSRV_OK;
 }
 
@@ -541,47 +492,42 @@ PVRSRV_ERROR SysFinalise(IMG_VOID)
        eError = EnableSGXClocksWrap(gpsSysData);
        if (eError != PVRSRV_OK)
        {
-               PVR_DPF((PVR_DBG_ERROR,"SysInitialise: Failed to Enable SGX clocks (%d)", eError));
-               (IMG_VOID)SysDeinitialise(gpsSysData);
-               gpsSysData = IMG_NULL;
+               PVR_DPF((PVR_DBG_ERROR,"SysFinalise: Failed to Enable SGX clocks (%d)", eError));
                return eError;
        }
 #endif 
 
-#if defined(SYS_USING_INTERRUPTS)
-
        eError = OSInstallMISR(gpsSysData);
        if (eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"SysFinalise: Failed to install MISR"));
-               (IMG_VOID)SysDeinitialise(gpsSysData);
-               gpsSysData = IMG_NULL;
                return eError;
        }
        SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_MISR);
 
+#if defined(SYS_USING_INTERRUPTS)
        
        eError = OSInstallDeviceLISR(gpsSysData, gsSGXDeviceMap.ui32IRQ, "SGX ISR", gpsSGXDevNode);
        if (eError != PVRSRV_OK)
        {
                PVR_DPF((PVR_DBG_ERROR,"SysFinalise: Failed to install ISR"));
-               (IMG_VOID)SysDeinitialise(gpsSysData);
-               gpsSysData = IMG_NULL;
                return eError;
        }
        SYS_SPECIFIC_DATA_SET(&gsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_LISR);
 #endif 
 
+#if defined(__linux__)
        
-       gpsSysData->pszVersionString = SysCreateVersionString(gsSGXDeviceMap.sRegsCpuPBase);
+       gpsSysData->pszVersionString = SysCreateVersionString();
        if (!gpsSysData->pszVersionString)
        {
                PVR_DPF((PVR_DBG_ERROR,"SysFinalise: Failed to create a system version string"));
        }
        else
        {
-               PVR_DPF((PVR_DBG_WARNING, "SysFinalise: Version string: %s", gpsSysData->pszVersionString));
+               PVR_TRACE(("SysFinalise: Version string: %s", gpsSysData->pszVersionString));
        }
+#endif
 
 #if defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
        
@@ -598,6 +544,14 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
 {
        PVRSRV_ERROR eError;
 
+       if(gpsSysData->pvSOCTimerRegisterKM)
+       {
+               OSUnReservePhys(gpsSysData->pvSOCTimerRegisterKM,
+                                               4,
+                                               PVRSRV_HAP_MULTI_PROCESS|PVRSRV_HAP_UNCACHED,
+                                               gpsSysData->hSOCTimerRegisterOSMemHandle);
+       }
+
 #if defined(SYS_USING_INTERRUPTS)
        if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_LISR))
        {
@@ -608,6 +562,7 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
                        return eError;
                }
        }
+#endif
 
        if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_MISR))
        {
@@ -618,9 +573,6 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
                        return eError;
                }
        }
-#else
-       PVR_UNREFERENCED_PARAMETER(psSysData);
-#endif 
 
        if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_INITDEV))
        {
@@ -643,14 +595,18 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
                        return eError;
                }
        }
-       
-#if defined(SGX_OCP_REGS_ENABLED)
-       OSUnMapPhysToLin(gpvOCPRegsLinAddr,
-                                        SYS_TI81xx_OCP_REGS_SIZE,
-                                        PVRSRV_HAP_UNCACHED|PVRSRV_HAP_KERNEL_ONLY,
-                                        IMG_NULL);
+#if 0
+       if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_PM_RUNTIME))
+       {
+               eError = SysPMRuntimeUnregister();
+               if (eError != PVRSRV_OK)
+               {
+                       PVR_DPF((PVR_DBG_ERROR,"SysDeinitialise: Failed to unregister with OSPM!"));
+                       gpsSysData = IMG_NULL;
+                       return eError;
+               }
+       }
 #endif
-
        
 
        if (SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_SYSCLOCKS))
@@ -668,23 +624,28 @@ PVRSRV_ERROR SysDeinitialise (SYS_DATA *psSysData)
                }
        }
 
-       if(gpsSysData->pvSOCTimerRegisterKM)
-       {
-               OSUnReservePhys(gpsSysData->pvSOCTimerRegisterKM,
-                                               4,
-                                               PVRSRV_HAP_MULTI_PROCESS|PVRSRV_HAP_UNCACHED,
-                                               gpsSysData->hSOCTimerRegisterOSMemHandle);
-       }
-
        SysDeinitialiseCommon(gpsSysData);
 
-#if defined(NO_HARDWARE)
-       if(SYS_SPECIFIC_DATA_TEST(gpsSysSpecificData, SYS_SPECIFIC_DATA_ENABLE_LOCATEDEV))
+#if defined(NO_HARDWARE) || defined(SGX_OCP_REGS_ENABLED)
+       if(gsSGXRegsCPUVAddr != IMG_NULL)
        {
+#if defined(NO_HARDWARE)
                
                OSBaseFreeContigMemory(SYS_TI81xx_SGX_REGS_SIZE, gsSGXRegsCPUVAddr, gsSGXDeviceMap.sRegsCpuPBase);
-       }
+#else
+#if defined(SGX_OCP_REGS_ENABLED)
+               OSUnMapPhysToLin(gsSGXRegsCPUVAddr,
+               gsSGXDeviceMap.ui32RegsSize,
+                                                                                                PVRSRV_HAP_UNCACHED|PVRSRV_HAP_KERNEL_ONLY,
+                                                                                                IMG_NULL);
+
+               gpvOCPRegsLinAddr = IMG_NULL;
 #endif
+#endif 
+               gsSGXRegsCPUVAddr = IMG_NULL;
+               gsSGXDeviceMap.pvRegsCpuVBase = gsSGXRegsCPUVAddr;
+       }
+#endif 
 
        
        gpsSysSpecificData->ui32SysSpecificData = 0;
@@ -804,14 +765,41 @@ IMG_UINT32 SysGetInterruptSource(SYS_DATA                 *psSysData,
 
 IMG_VOID SysClearInterrupts(SYS_DATA* psSysData, IMG_UINT32 ui32ClearBits)
 {
-       PVR_UNREFERENCED_PARAMETER(psSysData);
        PVR_UNREFERENCED_PARAMETER(ui32ClearBits);
-
+#if defined(NO_HARDWARE)
+       PVR_UNREFERENCED_PARAMETER(psSysData);
+#else
+#if defined(SGX_OCP_NO_INT_BYPASS)
+       OSWriteHWReg(gpvOCPRegsLinAddr, EUR_CR_OCP_IRQSTATUS_2, 0x1);
+#endif
        
-       OSReadHWReg(((PVRSRV_SGXDEV_INFO *)gpsSGXDevNode->pvDevice)->pvRegsBaseKM,
-                                                                               EUR_CR_EVENT_HOST_CLEAR);
+       OSReadHWReg(((PVRSRV_SGXDEV_INFO *)gpsSGXDevNode->pvDevice)->pvRegsBaseKM, EUR_CR_EVENT_HOST_CLEAR);
+#endif 
 }
 
+#if defined(SGX_OCP_NO_INT_BYPASS)
+IMG_VOID SysEnableSGXInterrupts(SYS_DATA *psSysData)
+{
+       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *)psSysData->pvSysSpecificData;
+       if (SYS_SPECIFIC_DATA_TEST(psSysSpecData, SYS_SPECIFIC_DATA_ENABLE_LISR) && !SYS_SPECIFIC_DATA_TEST(psSysSpecData, SYS_SPECIFIC_DATA_IRQ_ENABLED))
+       {
+               OSWriteHWReg(gpvOCPRegsLinAddr, EUR_CR_OCP_IRQSTATUS_2, 0x1);
+               OSWriteHWReg(gpvOCPRegsLinAddr, EUR_CR_OCP_IRQENABLE_SET_2, 0x1);
+               SYS_SPECIFIC_DATA_SET(psSysSpecData, SYS_SPECIFIC_DATA_IRQ_ENABLED);
+       }
+}
+
+IMG_VOID SysDisableSGXInterrupts(SYS_DATA *psSysData)
+{
+       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *)psSysData->pvSysSpecificData;
+
+       if (SYS_SPECIFIC_DATA_TEST(psSysSpecData, SYS_SPECIFIC_DATA_IRQ_ENABLED))
+       {
+               OSWriteHWReg(gpvOCPRegsLinAddr, EUR_CR_OCP_IRQENABLE_CLR_2, 0x1);
+               SYS_SPECIFIC_DATA_CLEAR(psSysSpecData, SYS_SPECIFIC_DATA_IRQ_ENABLED);
+       }
+}
+#endif 
 
 PVRSRV_ERROR SysSystemPrePowerState(PVRSRV_SYS_POWER_STATE eNewPowerState)
 {
index 22cf7e3..7e461b3 100644 (file)
@@ -27,7 +27,6 @@
 #if !defined(__SOCCONFIG_H__)
 #define __SOCCONFIG_H__
 
-#include "syscommon.h"
 
 #define VS_PRODUCT_NAME        "TI81xx"
 
index 79766ed..b6d3f5a 100644 (file)
@@ -1,6 +1,6 @@
 /**********************************************************************
  *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
+ * Copyright (C) Imagination Technologies Ltd. All rights reserved.
  * 
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
 
 #if defined(PVR_LINUX_USING_WORKQUEUES)
 #define MAX_HW_TIME_US                         (1000000)
+#define WAIT_TRY_COUNT                         (20000)
 #else
 #define MAX_HW_TIME_US                         (500000)
+#define WAIT_TRY_COUNT                         (10000)
 #endif
 
-#define WAIT_TRY_COUNT                         (10000)
 
-#define SYS_DEVICE_COUNT 3 
+#define SYS_DEVICE_COUNT 15 
 
 #endif 
index b05fc1c..0ae7ef5 100644 (file)
@@ -1,6 +1,6 @@
 /**********************************************************************
  *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
+ * Copyright (C) Imagination Technologies Ltd. All rights reserved.
  * 
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
 #endif 
 #endif 
 
+
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,35))
+#if !defined(LDM_PLATFORM)
+#error "LDM_PLATFORM must be set"
+#endif
+/*#define      PVR_LINUX_DYNAMIC_SGX_RESOURCE_INFO*/
+//#include <linux/platform_device.h>
+#endif
+
+#if ((defined(DEBUG) || defined(TIMING)) && \
+    (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,32))) && \
+    !defined(PVR_NO_OMAP_TIMER)
+#define        PVR_OMAP3_TIMING_PRCM
+#endif
+
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,35))
+/*#include <plat/gpu.h>*/
+#if !defined(PVR_NO_OMAP_TIMER)
+/*#define      PVR_OMAP_USE_DM_TIMER_API*/
+//#include <plat/dmtimer.h>
+#endif
+#endif
+
+#if !defined(PVR_NO_OMAP_TIMER)
+//#define PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA
+#endif
 #endif 
 
+#if !defined(NO_HARDWARE) && \
+     defined(SYS_USING_INTERRUPTS) && \
+     defined(SGX540)
+#define SGX_OCP_REGS_ENABLED
+#endif
+
+#if defined(__linux__)
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,35)) && defined(SGX_OCP_REGS_ENABLED)
+/*#define SGX_OCP_NO_INT_BYPASS*/
+#endif
+#endif
+
 #if defined (__cplusplus)
 extern "C" {
 #endif
 
  
  
-IMG_CHAR *SysCreateVersionString(IMG_CPU_PHYADDR sRegRegion);
-
 IMG_VOID DisableSystemClocks(SYS_DATA *psSysData);
 PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData);
 
@@ -76,6 +112,11 @@ PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData);
 
 #define        SYS_SPECIFIC_DATA_PM_UNINSTALL_LISR     0x00000200
 #define        SYS_SPECIFIC_DATA_PM_DISABLE_SYSCLOCKS  0x00000400
+#define SYS_SPECIFIC_DATA_ENABLE_OCPREGS       0x00000800
+#define SYS_SPECIFIC_DATA_ENABLE_PM_RUNTIME    0x00001000
+#if defined(SGX_OCP_REGS_ENABLED) && defined(SGX_OCP_NO_INT_BYPASS)
+#define SYS_SPECIFIC_DATA_IRQ_ENABLED          0x00002000
+#endif
 
 #define        SYS_SPECIFIC_DATA_SET(psSysSpecData, flag) ((IMG_VOID)((psSysSpecData)->ui32SysSpecificData |= (flag)))
 
@@ -88,6 +129,9 @@ typedef struct _SYS_SPECIFIC_DATA_TAG_
        IMG_UINT32      ui32SysSpecificData;
        PVRSRV_DEVICE_NODE *psSGXDevNode;
        IMG_BOOL        bSGXInitComplete;
+#if defined(PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA)
+       IMG_CPU_PHYADDR sTimerRegPhysBase;
+#endif
 #if !defined(__linux__)
        IMG_BOOL        bSGXClocksEnabled;
 #endif
@@ -105,27 +149,60 @@ typedef struct _SYS_SPECIFIC_DATA_TAG_
        atomic_t        sNotifyLockCPU;
        IMG_BOOL        bCallVDD2PostFunc;
 #endif
-       struct clk      *psCORE_CK;
-       struct clk      *psSGX_FCK;
-       struct clk      *psSGX_ICK;
-       struct clk      *psMPU_CK;
+       struct clk      *psCORE_CK;
+        struct clk      *psSGX_FCK;
+        struct clk      *psSGX_ICK;
+
 #if defined(DEBUG) || defined(TIMING)
        struct clk      *psGPT11_FCK;
        struct clk      *psGPT11_ICK;
 #endif
-#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,22))              
-       struct constraint_handle *pVdd2Handle;
-#endif 
+#if defined(PVR_OMAP_USE_DM_TIMER_API)
+       struct omap_dm_timer *psGPTimer;
+#endif
 #endif 
 } SYS_SPECIFIC_DATA;
 
 extern SYS_SPECIFIC_DATA *gpsSysSpecificData;
 
+#if defined(SGX_OCP_REGS_ENABLED) && defined(SGX_OCP_NO_INT_BYPASS)
+IMG_VOID SysEnableSGXInterrupts(SYS_DATA* psSysData);
+IMG_VOID SysDisableSGXInterrupts(SYS_DATA* psSysData);
+#else
+#define        SysEnableSGXInterrupts(psSysData)
+#define SysDisableSGXInterrupts(psSysData)
+#endif
+
 #if defined(SYS_CUSTOM_POWERLOCK_WRAP)
 IMG_BOOL WrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData);
 IMG_VOID UnwrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData);
 #endif
 
+#if defined(__linux__)
+
+PVRSRV_ERROR SysPMRuntimeRegister(void);
+PVRSRV_ERROR SysPMRuntimeUnregister(void);
+
+#else 
+
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(SysPMRuntimeRegister)
+#endif
+static INLINE PVRSRV_ERROR SysPMRuntimeRegister(void)
+{
+       return PVRSRV_OK;
+}
+
+#ifdef INLINE_IS_PRAGMA
+#pragma inline(SysPMRuntimeUnregister)
+#endif
+static INLINE PVRSRV_ERROR SysPMRuntimeUnregister(void)
+{
+       return PVRSRV_OK;
+}
+
+#endif 
+
 #if defined(__cplusplus)
 }
 #endif
index 7d81114..8736fcc 100644 (file)
@@ -1,6 +1,6 @@
 /**********************************************************************
  *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
+ * Copyright (C) Imagination Technologies Ltd. All rights reserved.
  * 
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
  ******************************************************************************/
 
 #if defined(__linux__)
-#if defined(PVR_LINUX_USING_WORKQUEUES)
-#include "sysutils_linux_wqueue_compat.c"
-#else
 #include "sysutils_linux.c"
 #endif
-#endif
 
index b3300fe..c9f0837 100644 (file)
@@ -1,6 +1,6 @@
 /**********************************************************************
  *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
+ * Copyright (C) Imagination Technologies Ltd. All rights reserved.
  * 
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
 #include <linux/clk.h>
 #include <linux/err.h>
 #include <linux/hardirq.h>
-#include <linux/spinlock.h>
-#include <asm/bug.h>
-
-#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26))
-#include <linux/semaphore.h>
-#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,31))
-//#include <plat/resource.h>
-#include <plat/omap-pm.h>
-#else 
-#include <mach/resource.h>
-#endif 
-#else 
-#include <asm/semaphore.h>
-#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,22))
-#include <asm/arch/resource.h>
-#endif 
-#endif 
+#include <linux/mutex.h>
 
-#if    (LINUX_VERSION_CODE >  KERNEL_VERSION(2,6,22)) && \
-       (LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,27))
-#define CONSTRAINT_NOTIFICATIONS
-#endif 
 #include "sgxdefs.h"
 #include "services_headers.h"
 #include "sysinfo.h"
 #include "sgxinfokm.h"
 #include "syslocal.h"
 
+//#include <linux/platform_device.h>
+//#include <linux/pm_runtime.h>
+
 #define        ONE_MHZ 1000000
 #define        HZ_TO_MHZ(m) ((m) / ONE_MHZ)
 
-#if defined(SUPPORT_OMAP3430_SGXFCLK_96M)
+#if defined(SUPPORT_TI81xx_SGXFCLK_96M)
 #define SGX_PARENT_CLOCK "cm_96m_fck"
 #else
 #define SGX_PARENT_CLOCK "core_ck"
 #endif
 
-//#define DEBUG
-#if !defined(PDUMP) && !defined(NO_HARDWARE)
-static IMG_BOOL PowerLockWrappedOnCPU(SYS_SPECIFIC_DATA *psSysSpecData)
-{
-       IMG_INT iCPU;
-       IMG_BOOL bLocked = IMG_FALSE;
-
-       if (!in_interrupt())
-       {
-               iCPU = get_cpu();
-               bLocked = (iCPU == atomic_read(&psSysSpecData->sPowerLockCPU));
-
-               put_cpu();
-       }
+#if defined(LDM_PLATFORM) && !defined(PVR_DRI_DRM_NOT_PCI)
+extern struct platform_device *gpsPVRLDMDev;
+#endif
 
-       return bLocked;
-}
 
-static IMG_VOID PowerLockWrap(SYS_SPECIFIC_DATA *psSysSpecData)
+static PVRSRV_ERROR PowerLockWrap(SYS_SPECIFIC_DATA *psSysSpecData, IMG_BOOL bTryLock)
 {
-       IMG_INT iCPU;
-
-       if (!in_interrupt())
-       {
-               
-               iCPU = get_cpu();
-
-               
-               PVR_ASSERT(iCPU != -1);
-
-               PVR_ASSERT(!PowerLockWrappedOnCPU(psSysSpecData));
-
-               spin_lock(&psSysSpecData->sPowerLock);
+        if (!in_interrupt())
+        {
+                if (bTryLock)
+                {
+                        int locked = mutex_trylock(&psSysSpecData->sPowerLock);
+                        if (locked == 0)
+                        {
+                                return PVRSRV_ERROR_RETRY;
+                        }
+                }
+                else
+                {
+                        mutex_lock(&psSysSpecData->sPowerLock);
+                }
+        }
 
-               atomic_set(&psSysSpecData->sPowerLockCPU, iCPU);
-       }
+        return PVRSRV_OK;
 }
 
 static IMG_VOID PowerLockUnwrap(SYS_SPECIFIC_DATA *psSysSpecData)
 {
-       if (!in_interrupt())
-       {
-               PVR_ASSERT(PowerLockWrappedOnCPU(psSysSpecData));
-
-               atomic_set(&psSysSpecData->sPowerLockCPU, -1);
-
-               spin_unlock(&psSysSpecData->sPowerLock);
-
-               put_cpu();
-       }
+        if (!in_interrupt())
+        {
+                mutex_unlock(&psSysSpecData->sPowerLock);
+        }
 }
 
-PVRSRV_ERROR SysPowerLockWrap(SYS_DATA *psSysData)
+PVRSRV_ERROR SysPowerLockWrap(IMG_BOOL bTryLock)
 {
-       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
+        SYS_DATA        *psSysData;
 
-       PowerLockWrap(psSysSpecData);
+        SysAcquireData(&psSysData);
 
-       return PVRSRV_OK;
+        return PowerLockWrap(psSysData->pvSysSpecificData, bTryLock);
 }
 
-IMG_VOID SysPowerLockUnwrap(SYS_DATA *psSysData)
+IMG_VOID SysPowerLockUnwrap(IMG_VOID)
 {
-       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
+        SYS_DATA        *psSysData;
 
-       PowerLockUnwrap(psSysSpecData);
-}
-#else  
-static IMG_BOOL PowerLockWrappedOnCPU(SYS_SPECIFIC_DATA unref__ *psSysSpecData)
-{
-       return IMG_FALSE;
-}
+        SysAcquireData(&psSysData);
 
-static IMG_VOID PowerLockWrap(SYS_SPECIFIC_DATA unref__ *psSysSpecData)
-{
+        PowerLockUnwrap(psSysData->pvSysSpecificData);
 }
 
-static IMG_VOID PowerLockUnwrap(SYS_SPECIFIC_DATA unref__ *psSysSpecData)
-{
-}
 
-PVRSRV_ERROR SysPowerLockWrap(SYS_DATA unref__ *psSysData)
-{
-       return PVRSRV_OK;
-}
 
-IMG_VOID SysPowerLockUnwrap(SYS_DATA unref__ *psSysData)
-{
-}
-#endif 
 
 IMG_BOOL WrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData)
 {
-       IMG_BOOL bPowerLock = PowerLockWrappedOnCPU(psSysSpecData);
-
-       if (bPowerLock)
-       {
-               PowerLockUnwrap(psSysSpecData);
-       }
-
-       return bPowerLock;
+       return IMG_TRUE;
 }
 
 IMG_VOID UnwrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData)
 {
-       PowerLockWrap(psSysSpecData);
 }
 
 static inline IMG_UINT32 scale_by_rate(IMG_UINT32 val, IMG_UINT32 rate1, IMG_UINT32 rate2)
@@ -187,48 +126,37 @@ static inline IMG_UINT32 scale_by_rate(IMG_UINT32 val, IMG_UINT32 rate1, IMG_UIN
 
 static inline IMG_UINT32 scale_prop_to_SGX_clock(IMG_UINT32 val, IMG_UINT32 rate)
 {
-
         if(cpu_is_ti816x())
         {
-               return scale_by_rate(val, rate, SYS_389x_SGX_CLOCK_SPEED);
+       return scale_by_rate(val, rate, SYS_389x_SGX_CLOCK_SPEED);
         }
         else
         {
-               return scale_by_rate(val, rate, SYS_387x_SGX_CLOCK_SPEED);
+       return scale_by_rate(val, rate, SYS_387x_SGX_CLOCK_SPEED);
         }
+
 }
 
 static inline IMG_UINT32 scale_inv_prop_to_SGX_clock(IMG_UINT32 val, IMG_UINT32 rate)
 {
         if(cpu_is_ti816x())
-        {
-               return scale_by_rate(val, SYS_389x_SGX_CLOCK_SPEED, rate);
-       }
+       return scale_by_rate(val, SYS_389x_SGX_CLOCK_SPEED, rate);
        else
-       {
-               return scale_by_rate(val, SYS_387x_SGX_CLOCK_SPEED, rate);
-       }
+       return scale_by_rate(val, SYS_387x_SGX_CLOCK_SPEED, rate);
+
 }
 
 IMG_VOID SysGetSGXTimingInformation(SGX_TIMING_INFORMATION *psTimingInfo)
 {
        IMG_UINT32 rate;
 
-#if defined(NO_HARDWARE)
         if(cpu_is_ti816x())
-        {
-               rate = SYS_389x_SGX_CLOCK_SPEED;
-       }
+       rate = SYS_389x_SGX_CLOCK_SPEED;
        else
-       {
-               rate = SYS_387x_SGX_CLOCK_SPEED;
-       }
+       rate = SYS_387x_SGX_CLOCK_SPEED;
 
-#else
+#if !defined(NO_HARDWARE)
        PVR_ASSERT(atomic_read(&gpsSysSpecificData->sSGXClocksEnabled) != 0);
-
-       rate = clk_get_rate(gpsSysSpecificData->psSGX_FCK);
-       PVR_ASSERT(rate != 0);
 #endif
        psTimingInfo->ui32CoreClockSpeed = rate;
        psTimingInfo->ui32HWRecoveryFreq = scale_prop_to_SGX_clock(SYS_SGX_HWRECOVERY_TIMEOUT_FREQ, rate);
@@ -241,212 +169,12 @@ IMG_VOID SysGetSGXTimingInformation(SGX_TIMING_INFORMATION *psTimingInfo)
        psTimingInfo->ui32ActivePowManLatencyms = SYS_SGX_ACTIVE_POWER_LATENCY_MS;
 }
 
-#if defined(CONSTRAINT_NOTIFICATIONS)
-#if !defined(SGX_DYNAMIC_TIMING_INFO)
-#error "SGX_DYNAMIC_TIMING_INFO must be defined for this platform"
-#endif
-
-static struct constraint_id cnstr_id_vdd2 = {
-       .type = RES_OPP_CO,
-       .data = (IMG_VOID *)"vdd2_opp"
-};
-
-#if !defined(PDUMP) && !defined(NO_HARDWARE)
-static inline IMG_BOOL ConstraintNotificationsEnabled(SYS_SPECIFIC_DATA *psSysSpecData)
-{
-       return (atomic_read(&psSysSpecData->sSGXClocksEnabled) != 0) && psSysSpecData->bSGXInitComplete && psSysSpecData->bConstraintNotificationsEnabled;
-
-}
-
-static IMG_BOOL NotifyLockedOnCPU(SYS_SPECIFIC_DATA *psSysSpecData)
-{
-       IMG_INT iCPU = get_cpu();
-       IMG_BOOL bLocked = (iCPU == atomic_read(&psSysSpecData->sNotifyLockCPU));
-
-       put_cpu();
-
-       return bLocked;
-}
-
-static IMG_VOID NotifyLock(SYS_SPECIFIC_DATA *psSysSpecData)
-{
-       IMG_INT iCPU;
-
-       BUG_ON(in_interrupt());
-
-       
-       iCPU = get_cpu();
-
-       
-       PVR_ASSERT(iCPU != -1);
-
-       PVR_ASSERT(!NotifyLockedOnCPU(psSysSpecData));
-
-       spin_lock(&psSysSpecData->sNotifyLock);
-
-       atomic_set(&psSysSpecData->sNotifyLockCPU, iCPU);
-}
-
-static IMG_VOID NotifyUnlock(SYS_SPECIFIC_DATA *psSysSpecData)
-{
-       PVR_ASSERT(NotifyLockedOnCPU(psSysSpecData));
-
-       atomic_set(&psSysSpecData->sNotifyLockCPU, -1);
-
-       spin_unlock(&psSysSpecData->sNotifyLock);
-
-       put_cpu();
-}
-
-static int VDD2PostFunc(struct notifier_block *n, unsigned long event, IMG_VOID *ptr)
-{
-       PVR_UNREFERENCED_PARAMETER(n);
-       PVR_UNREFERENCED_PARAMETER(event);
-       PVR_UNREFERENCED_PARAMETER(ptr);
-
-       if (in_interrupt())
-       {
-               PVR_DPF((PVR_DBG_ERROR, "%s Called in interrupt context.  Ignoring.", __FUNCTION__));
-               return 0;
-       }
-
-       
-       if (!NotifyLockedOnCPU(gpsSysSpecificData))
-       {
-               return 0;
-       }
-
-#if defined(DEBUG)
-       if (ConstraintNotificationsEnabled(gpsSysSpecificData))
-       {
-               IMG_UINT32 rate;
-
-               rate = clk_get_rate(gpsSysSpecificData->psSGX_FCK);
-
-               PVR_ASSERT(rate != 0);
-
-               PVR_DPF((PVR_DBG_MESSAGE, "%s: SGX clock rate: %dMHz", __FUNCTION__, HZ_TO_MHZ(rate)));
-       }
-#endif
-       if (gpsSysSpecificData->bCallVDD2PostFunc)
-       {
-               PVRSRVDevicePostClockSpeedChange(gpsSysSpecificData->psSGXDevNode->sDevId.ui32DeviceIndex, IMG_TRUE, IMG_NULL);
-
-               gpsSysSpecificData->bCallVDD2PostFunc = IMG_FALSE;
-       }
-       else
-       {
-               if (ConstraintNotificationsEnabled(gpsSysSpecificData))
-               {
-                       PVR_TRACE(("%s: Not calling PVR clock speed notification functions", __FUNCTION__));
-               }
-       }
-
-       NotifyUnlock(gpsSysSpecificData);
-
-       return 0;
-}
-
-static int VDD2PreFunc(struct notifier_block *n, unsigned long event, IMG_VOID *ptr)
-{
-       PVR_UNREFERENCED_PARAMETER(n);
-       PVR_UNREFERENCED_PARAMETER(event);
-       PVR_UNREFERENCED_PARAMETER(ptr);
-
-       if (in_interrupt())
-       {
-               PVR_DPF((PVR_DBG_WARNING, "%s Called in interrupt context.  Ignoring.", __FUNCTION__));
-               return 0;
-       }
-
-       if (PowerLockWrappedOnCPU(gpsSysSpecificData))
-       {
-               PVR_DPF((PVR_DBG_WARNING, "%s Called from within a power transition.  Ignoring.", __FUNCTION__));
-               return 0;
-       }
-
-       NotifyLock(gpsSysSpecificData);
-
-       PVR_ASSERT(!gpsSysSpecificData->bCallVDD2PostFunc);
-
-       if (ConstraintNotificationsEnabled(gpsSysSpecificData))
-       {
-               PVRSRV_ERROR eError;
-
-               eError = PVRSRVDevicePreClockSpeedChange(gpsSysSpecificData->psSGXDevNode->sDevId.ui32DeviceIndex, IMG_TRUE, IMG_NULL);
-
-               gpsSysSpecificData->bCallVDD2PostFunc = (eError == PVRSRV_OK);
-
-       }
-
-       return 0;
-}
-
-static struct notifier_block sVDD2Pre = {
-       VDD2PreFunc,
-        NULL
-};
-
-static struct notifier_block sVDD2Post = {
-       VDD2PostFunc,
-        NULL
-};
-
-static IMG_VOID RegisterConstraintNotifications(IMG_VOID)
-{
-       PVR_TRACE(("Registering constraint notifications"));
-
-       PVR_ASSERT(!gpsSysSpecificData->bConstraintNotificationsEnabled);
-
-       constraint_register_pre_notification(gpsSysSpecificData->pVdd2Handle, &sVDD2Pre,
-                                               max_vdd2_opp+1);
-
-       constraint_register_post_notification(gpsSysSpecificData->pVdd2Handle, &sVDD2Post,
-                                               max_vdd2_opp+1);
-
-       
-       NotifyLock(gpsSysSpecificData);
-       gpsSysSpecificData->bConstraintNotificationsEnabled = IMG_TRUE;
-       NotifyUnlock(gpsSysSpecificData);
-
-       PVR_TRACE(("VDD2 constraint notifications registered"));
-}
-
-static IMG_VOID UnRegisterConstraintNotifications(IMG_VOID)
-{
-       PVR_TRACE(("Unregistering constraint notifications"));
-
-       
-       NotifyLock(gpsSysSpecificData);
-       gpsSysSpecificData->bConstraintNotificationsEnabled = IMG_FALSE;
-       NotifyUnlock(gpsSysSpecificData);
-
-       
-       constraint_unregister_pre_notification(gpsSysSpecificData->pVdd2Handle, &sVDD2Pre,
-                                               max_vdd2_opp+1);
-
-       constraint_unregister_post_notification(gpsSysSpecificData->pVdd2Handle, &sVDD2Post,
-                                               max_vdd2_opp+1);
-}
-#else
-static IMG_VOID RegisterConstraintNotifications(IMG_VOID)
-{
-}
-
-static IMG_VOID UnRegisterConstraintNotifications(IMG_VOID)
-{
-}
-#endif 
-#endif 
-
 PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData)
 {
 #if !defined(NO_HARDWARE)
        SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
-       long lNewRate;
-       long lRate;
        IMG_INT res;
-
+       long lRate,lNewRate;
        
        if (atomic_read(&psSysSpecData->sSGXClocksEnabled) != 0)
        {
@@ -454,42 +182,56 @@ PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData)
        }
 
        PVR_DPF((PVR_DBG_MESSAGE, "EnableSGXClocks: Enabling SGX Clocks"));
-
-       res = clk_enable(psSysSpecData->psSGX_FCK);
+       
+       res=clk_enable(psSysSpecData->psSGX_FCK);
        if (res < 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: Couldn't enable SGX functional clock (%d)", res));
-               return PVRSRV_ERROR_UNABLE_TO_ENABLE_CLOCK;
-       }
+        {
+                PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: Couldn't enable SGX functional clock (%d)", res));
+                return PVRSRV_ERROR_UNABLE_TO_ENABLE_CLOCK;
+        }
+if(cpu_is_ti816x())    
+       lNewRate = clk_round_rate(psSysSpecData->psSGX_FCK, SYS_389x_SGX_CLOCK_SPEED + ONE_MHZ);
+else
+       lNewRate = clk_round_rate(psSysSpecData->psSGX_FCK, SYS_387x_SGX_CLOCK_SPEED + ONE_MHZ);
+        if (lNewRate <= 0)
+        {
+                PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: Couldn't round SGX functional clock rate"));
+                return PVRSRV_ERROR_UNABLE_TO_ROUND_CLOCK_RATE;
+        }
 
-#if 0
-       lNewRate = clk_round_rate(psSysSpecData->psSGX_FCK, SYS_SGX_CLOCK_SPEED + ONE_MHZ);
-       if (lNewRate <= 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: Couldn't round SGX functional clock rate"));
-               return PVRSRV_ERROR_UNABLE_TO_ROUND_CLOCK_RATE;
-       }
 
-       
-       lRate = clk_get_rate(psSysSpecData->psSGX_FCK);
-       if (lRate != lNewRate)
-       {
-               res = clk_set_rate(psSysSpecData->psSGX_FCK, lNewRate);
-               if (res < 0)
-               {
-                       PVR_DPF((PVR_DBG_WARNING, "EnableSGXClocks: Couldn't set SGX functional clock rate (%d)", res));
-               }
-       }
-#endif
+        lRate = clk_get_rate(psSysSpecData->psSGX_FCK);
+        if (lRate != lNewRate)
+        {
+                res = clk_set_rate(psSysSpecData->psSGX_FCK, lNewRate);
+                if (res < 0)
+                {
+                        PVR_DPF((PVR_DBG_WARNING, "EnableSGXClocks: Couldn't set SGX functional clock rate (%d)", res));
+                       return PVRSRV_ERROR_UNABLE_TO_SET_CLOCK_RATE;
+                }
+        }
 
-//             IMG_UINT32 rate = clk_get_rate(psSysSpecData->psSGX_FCK);
-//             PVR_TRACE((PVR_DBG_MESSAGE, "EnableSGXClocks: SGX Functional Clock is %dMhz", HZ_TO_MHZ(rate)));
 #if defined(DEBUG)
+        {
+                IMG_UINT32 rate = clk_get_rate(psSysSpecData->psSGX_FCK);
+                PVR_DPF((PVR_DBG_MESSAGE, "EnableSGXClocks: SGX Functional Clock is %dMhz", HZ_TO_MHZ(rate)));
+        }
+#endif
+
+
+
+#if defined(LDM_PLATFORM) && !defined(PVR_DRI_DRM_NOT_PCI)
        {
-               IMG_UINT32 rate = clk_get_rate(psSysSpecData->psSGX_FCK);
-               PVR_DPF((PVR_DBG_MESSAGE, "EnableSGXClocks: SGX Functional Clock is %dMhz", HZ_TO_MHZ(rate)));
+               
+//             int res = pm_runtime_get_sync(&gpsPVRLDMDev->dev);
+//             if (res < 0)
+//             {
+//                     PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: pm_runtime_get_sync failed (%d)", -res));
+//                     return PVRSRV_ERROR_UNABLE_TO_ENABLE_CLOCK;
+//             }
        }
 #endif
+//     SysEnableSGXInterrupts(psSysData);
 
        
        atomic_set(&psSysSpecData->sSGXClocksEnabled, 1);
@@ -506,20 +248,29 @@ IMG_VOID DisableSGXClocks(SYS_DATA *psSysData)
 #if !defined(NO_HARDWARE)
        SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
 
-       
        if (atomic_read(&psSysSpecData->sSGXClocksEnabled) == 0)
        {
                return;
        }
-
+       
        PVR_DPF((PVR_DBG_MESSAGE, "DisableSGXClocks: Disabling SGX Clocks"));
+       
+       clk_disable(psSysSpecData->psSGX_FCK);
+
+       clk_disable(psSysSpecData->psSGX_ICK);
 
-       if (psSysSpecData->psSGX_FCK)
+//     SysDisableSGXInterrupts(psSysData);
+
+#if defined(LDM_PLATFORM) && !defined(PVR_DRI_DRM_NOT_PCI)
        {
-               clk_disable(psSysSpecData->psSGX_FCK);
+//             int res = pm_runtime_put_sync(&gpsPVRLDMDev->dev);
+//             if (res < 0)
+//             {
+//                     PVR_DPF((PVR_DBG_ERROR, "DisableSGXClocks: pm_runtime_put_sync failed (%d)", -res));
+//             }
        }
+#endif
 
-       
        atomic_set(&psSysSpecData->sSGXClocksEnabled, 0);
 
 #else  
@@ -527,90 +278,93 @@ IMG_VOID DisableSGXClocks(SYS_DATA *psSysData)
 #endif 
 }
 
-PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
+#if (defined(DEBUG) || defined(TIMING)) && !defined(PVR_NO_OMAP_TIMER)
+#if defined(PVR_OMAP_USE_DM_TIMER_API)
+#define        GPTIMER_TO_USE 11
+static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
 {
-       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
-       struct clk *psCLK;
-       IMG_INT res;
-       PVRSRV_ERROR eError;
-       IMG_BOOL bPowerLock;
+       PVR_ASSERT(psSysSpecData->psGPTimer == NULL);
 
-#if defined(DEBUG) || defined(TIMING)
-       IMG_INT rate;
-       struct clk *sys_ck;
-       IMG_CPU_PHYADDR     TimerRegPhysBase;
-       IMG_HANDLE hTimerEnable;
-       IMG_UINT32 *pui32TimerEnable;
+       
+       psSysSpecData->psGPTimer = omap_dm_timer_request_specific(GPTIMER_TO_USE);
+       if (psSysSpecData->psGPTimer == NULL)
+       {
+       
+               PVR_DPF((PVR_DBG_WARNING, "%s: omap_dm_timer_request_specific failed", __FUNCTION__));
+               return PVRSRV_ERROR_CLOCK_REQUEST_FAILED;
+       }
 
-#endif 
+       
+       omap_dm_timer_set_source(psSysSpecData->psGPTimer, OMAP_TIMER_SRC_SYS_CLK);
+       omap_dm_timer_enable(psSysSpecData->psGPTimer);
 
-       PVR_TRACE(("EnableSystemClocks: Enabling System Clocks"));
+       
+       omap_dm_timer_set_load_start(psSysSpecData->psGPTimer, 1, 0);
 
-       if (!psSysSpecData->bSysClocksOneTimeInit)
-       {
-               bPowerLock = IMG_FALSE;
+       omap_dm_timer_start(psSysSpecData->psGPTimer);
 
-               spin_lock_init(&psSysSpecData->sPowerLock);
-               atomic_set(&psSysSpecData->sPowerLockCPU, -1);
-               spin_lock_init(&psSysSpecData->sNotifyLock);
-               atomic_set(&psSysSpecData->sNotifyLockCPU, -1);
+       
+       psSysSpecData->sTimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_REGS_SYS_PHYS_BASE;
 
-               atomic_set(&psSysSpecData->sSGXClocksEnabled, 0);
-                
-               psCLK = clk_get(NULL, "sgx_ck");
-               
-                if (IS_ERR(psCLK))
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "EnableSsystemClocks: Couldn't get SGX Functional Clock"));
-                       goto ExitError;
-               }
-               psSysSpecData->psSGX_FCK = psCLK;
+       return PVRSRV_OK;
+}
 
-               psSysSpecData->bSysClocksOneTimeInit = IMG_TRUE;
-       }
-       else
+static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
+{
+       if (psSysSpecData->psGPTimer != NULL)
        {
-               
-               bPowerLock = PowerLockWrappedOnCPU(psSysSpecData);
-               if (bPowerLock)
-               {
-                       PowerLockUnwrap(psSysSpecData);
-               }
-       }
+                       
+               (void) omap_dm_timer_stop(psSysSpecData->psGPTimer);
 
-#if defined(CONSTRAINT_NOTIFICATIONS)
-       psSysSpecData->pVdd2Handle = constraint_get(PVRSRV_MODNAME, &cnstr_id_vdd2);
-       if (IS_ERR(psSysSpecData->pVdd2Handle))
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't get VDD2 constraint handle"));
-               goto ExitError;
+               omap_dm_timer_disable(psSysSpecData->psGPTimer);
+
+               omap_dm_timer_free(psSysSpecData->psGPTimer);
+
+               psSysSpecData->sTimerRegPhysBase.uiAddr = 0;
+
+               psSysSpecData->psGPTimer = NULL;
        }
 
-       RegisterConstraintNotifications();
+}
+#else  
+static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
+{
+#if defined(PVR_OMAP3_TIMING_PRCM)
+       struct clk *psCLK;
+       IMG_INT res;
+       struct clk *sys_ck;
+       IMG_INT rate;
+#endif
+       PVRSRV_ERROR eError;
+
+       IMG_CPU_PHYADDR sTimerRegPhysBase;
+       IMG_HANDLE hTimerEnable;
+       IMG_UINT32 *pui32TimerEnable;
+#if defined(PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA)
+       PVR_ASSERT(psSysSpecData->sTimerRegPhysBase.uiAddr == 0);
 #endif
 
-#if defined(DEBUG) || defined(TIMING)
-        if(cpu_is_ti816x()) {
-                psCLK = clk_get(NULL, "gpt6_fck");
-        } else {
-                psCLK = clk_get(NULL, "gpt7_fck");
-        }
+
+#if defined(PVR_OMAP3_TIMING_PRCM)
+if(cpu_is_ti816x())    
+       psCLK = clk_get(NULL, "gpt6_fck");
+else
+       psCLK = clk_get(NULL, "gpt6_fck");
        if (IS_ERR(psCLK))
        {
                PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't get GPTIMER11 functional clock"));
-               goto ExitUnRegisterConstraintNotifications;
+               goto ExitError;
        }
        psSysSpecData->psGPT11_FCK = psCLK;
 
-        if(cpu_is_ti816x()) {
-                psCLK = clk_get(NULL, "gpt6_ick");
-        } else {
-                psCLK = clk_get(NULL, "gpt7_ick");
-        }
+if(cpu_is_ti816x())    
+       psCLK = clk_get(NULL, "gpt6_ick");
+else
+       psCLK = clk_get(NULL, "gpt7_ick");
        if (IS_ERR(psCLK))
        {
                PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't get GPTIMER11 interface clock"));
-               goto ExitUnRegisterConstraintNotifications;
+               goto ExitError;
        }
        psSysSpecData->psGPT11_ICK = psCLK;
 
@@ -621,7 +375,7 @@ PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
        if (res < 0)
        {
                PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't enable GPTIMER11 functional clock (%d)", res));
-               goto ExitUnRegisterConstraintNotifications;
+               goto ExitError;
        }
 
        res = clk_enable(psSysSpecData->psGPT11_ICK);
@@ -630,10 +384,11 @@ PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
                PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't enable GPTIMER11 interface clock (%d)", res));
                goto ExitDisableGPT11FCK;
        }
+#endif 
 
        
-       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_TSICR_SYS_PHYS_BASE;
-       pui32TimerEnable = OSMapPhysToLin(TimerRegPhysBase,
+       sTimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_TSICR_SYS_PHYS_BASE;
+       pui32TimerEnable = OSMapPhysToLin(sTimerRegPhysBase,
                   4,
                   PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
                   &hTimerEnable);
@@ -644,13 +399,12 @@ PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
                goto ExitDisableGPT11ICK;
        }
 
-       rate = *pui32TimerEnable;
-       if(!(rate & 4))
+       if(!(*pui32TimerEnable & 4))
        {
                PVR_TRACE(("Setting GPTIMER11 mode to posted (currently is non-posted)"));
 
                
-               *pui32TimerEnable = rate | 4;
+               *pui32TimerEnable |= 4;
        }
 
        OSUnMapPhysToLin(pui32TimerEnable,
@@ -659,8 +413,8 @@ PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
                    hTimerEnable);
 
        
-       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_ENABLE_SYS_PHYS_BASE;
-       pui32TimerEnable = OSMapPhysToLin(TimerRegPhysBase,
+       sTimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_ENABLE_SYS_PHYS_BASE;
+       pui32TimerEnable = OSMapPhysToLin(sTimerRegPhysBase,
                   4,
                   PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
                   &hTimerEnable);
@@ -671,99 +425,44 @@ PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
                goto ExitDisableGPT11ICK;
        }
 
-       
        *pui32TimerEnable = 3;
 
        OSUnMapPhysToLin(pui32TimerEnable,
                    4,
                    PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
                    hTimerEnable);
-
-#endif 
-
-#if defined(PDUMP) && !defined(NO_HARDWARE) && defined(CONSTRAINT_NOTIFICATIONS)
-       PVR_TRACE(("EnableSystemClocks: Setting SGX OPP constraint"));
-
-       
-       res = constraint_set(psSysSpecData->pVdd2Handle, max_vdd2_opp);
-       if (res != 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: constraint_set failed (%d)", res));
-               goto ExitConstraintSetFailed;
-       }
+#if defined(PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA)
+       psSysSpecData->sTimerRegPhysBase = sTimerRegPhysBase;
 #endif
+
        eError = PVRSRV_OK;
+
        goto Exit;
 
-#if defined(PDUMP) && !defined(NO_HARDWARE) && defined(CONSTRAINT_NOTIFICATIONS)
-ExitConstraintSetFailed:
-#endif
-#if defined(DEBUG) || defined(TIMING)
 ExitDisableGPT11ICK:
+#if defined(PVR_OMAP3_TIMING_PRCM)
        clk_disable(psSysSpecData->psGPT11_ICK);
 ExitDisableGPT11FCK:
        clk_disable(psSysSpecData->psGPT11_FCK);
-ExitUnRegisterConstraintNotifications:
+ExitError:
 #endif 
-#if defined(CONSTRAINT_NOTIFICATIONS)
-       UnRegisterConstraintNotifications();
-       constraint_put(psSysSpecData->pVdd2Handle);
-#endif
+       eError = PVRSRV_ERROR_CLOCK_REQUEST_FAILED;
 Exit:
-       if (bPowerLock)
-       {
-               PowerLockWrap(psSysSpecData);
-       }
-
-ExitError:
-       eError = PVRSRV_ERROR_DISABLE_CLOCK_FAILURE;
        return eError;
 }
 
-IMG_VOID DisableSystemClocks(SYS_DATA *psSysData)
+static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
 {
-       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
-       IMG_BOOL bPowerLock;
-#if defined(DEBUG) || defined(TIMING)
-       IMG_CPU_PHYADDR TimerRegPhysBase;
        IMG_HANDLE hTimerDisable;
        IMG_UINT32 *pui32TimerDisable;
-#endif 
-
-       PVR_TRACE(("DisableSystemClocks: Disabling System Clocks"));
-
-       
-       DisableSGXClocks(psSysData);
-
-       bPowerLock = PowerLockWrappedOnCPU(psSysSpecData);
-       if (bPowerLock)
-       {
-               
-               PowerLockUnwrap(psSysSpecData);
-       }
-
-#if defined(PDUMP) && !defined(NO_HARDWARE) && defined(CONSTRAINT_NOTIFICATIONS)
+       IMG_CPU_PHYADDR TimerRegPhysBase;
+#if defined(PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA)
+       if (psSysSpecData->sTimerRegPhysBase.uiAddr == 0)
        {
-               int res;
-
-               PVR_TRACE(("DisableSystemClocks: Removing SGX OPP constraint"));
-
-               
-               res = constraint_remove(psSysSpecData->pVdd2Handle);
-               if (res != 0)
-               {
-                       PVR_DPF((PVR_DBG_WARNING, "DisableSystemClocks: constraint_remove failed (%d)", res));
-               }
+               return;
        }
 #endif
-
-#if defined(CONSTRAINT_NOTIFICATIONS)
-       UnRegisterConstraintNotifications();
-#endif
-
-#if defined(DEBUG) || defined(TIMING)
-       
-       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_ENABLE_SYS_PHYS_BASE;
+       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_ENABLE_SYS_PHYS_BASE;     
        pui32TimerDisable = OSMapPhysToLin(TimerRegPhysBase,
                                4,
                                PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
@@ -783,16 +482,78 @@ IMG_VOID DisableSystemClocks(SYS_DATA *psSysData)
                                hTimerDisable);
        }
 
+#if defined(PVR_OMAP_TIMER_BASE_IN_SYS_SPEC_DATA)
+       psSysSpecData->sTimerRegPhysBase.uiAddr = 0;
+#endif
+
+#if defined(PVR_OMAP3_TIMING_PRCM)
        clk_disable(psSysSpecData->psGPT11_ICK);
 
        clk_disable(psSysSpecData->psGPT11_FCK);
-
+#endif 
+}
+#endif 
+#else  
+static PVRSRV_ERROR AcquireGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
+{
+       PVR_UNREFERENCED_PARAMETER(psSysSpecData);
+       return PVRSRV_OK;
+}
+static void ReleaseGPTimer(SYS_SPECIFIC_DATA *psSysSpecData)
+{
+       PVR_UNREFERENCED_PARAMETER(psSysSpecData);
+}
 #endif 
-#if defined(CONSTRAINT_NOTIFICATIONS)
-       constraint_put(psSysSpecData->pVdd2Handle);
-#endif
-       if (bPowerLock)
+
+PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
+{
+       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
+       struct clk *psCLK;
+       PVR_TRACE(("EnableSystemClocks: Enabling System Clocks"));
+
+       if (!psSysSpecData->bSysClocksOneTimeInit)
        {
-               PowerLockWrap(psSysSpecData);
+               mutex_init(&psSysSpecData->sPowerLock);
+
+               atomic_set(&psSysSpecData->sSGXClocksEnabled, 0);
+
+
+               psCLK = clk_get(NULL, "sgx_ck");
+                if (IS_ERR(psCLK))
+                {
+                        PVR_DPF((PVR_DBG_ERROR, "EnableSsystemClocks: Couldn't get SGX Functional Clock"));
+                        return PVRSRV_ERROR_UNABLE_TO_GET_CLOCK;
+                }
+                psSysSpecData->psSGX_FCK = psCLK;
+
        }
+
+       return AcquireGPTimer(psSysSpecData);
+}
+
+IMG_VOID DisableSystemClocks(SYS_DATA *psSysData)
+{
+       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
+       PVR_TRACE(("DisableSystemClocks: Disabling System Clocks"));
+       
+       DisableSGXClocks(psSysData);
+
+       ReleaseGPTimer(psSysSpecData);
+
+}
+
+PVRSRV_ERROR SysPMRuntimeRegister(void)
+{
+#if defined(LDM_PLATFORM) && !defined(PVR_DRI_DRM_NOT_PCI)
+//     pm_runtime_enable(&gpsPVRLDMDev->dev);
+#endif
+       return PVRSRV_OK;
+}
+
+PVRSRV_ERROR SysPMRuntimeUnregister(void)
+{
+#if defined(LDM_PLATFORM) && !defined(PVR_DRI_DRM_NOT_PCI)
+//     pm_runtime_disable(&gpsPVRLDMDev->dev);
+#endif
+       return PVRSRV_OK;
 }
diff --git a/services4/system/ti81xx/sysutils_linux_wqueue_compat.c b/services4/system/ti81xx/sysutils_linux_wqueue_compat.c
deleted file mode 100644 (file)
index 10f819a..0000000
+++ /dev/null
@@ -1,578 +0,0 @@
-/**********************************************************************
- *
- * Copyright(c) 2008 Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
-#include <linux/version.h>
-#include <linux/clk.h>
-#include <linux/err.h>
-#include <linux/hardirq.h>
-#include <linux/mutex.h>
-
-#include "sgxdefs.h"
-#include "services_headers.h"
-#include "sysinfo.h"
-#include "sgxapi_km.h"
-#include "sysconfig.h"
-#include "sgxinfokm.h"
-#include "syslocal.h"
-
-#if !defined(PVR_LINUX_USING_WORKQUEUES)
-#error "PVR_LINUX_USING_WORKQUEUES must be defined"
-#endif
-
-#define        ONE_MHZ 1000000
-#define        HZ_TO_MHZ(m) ((m) / ONE_MHZ)
-
-#if defined(SUPPORT_OMAP3430_SGXFCLK_96M)
-#define SGX_PARENT_CLOCK "cm_96m_fck"
-#else
-#define SGX_PARENT_CLOCK "core_ck"
-#endif
-
-static PVRSRV_ERROR PowerLockWrap(SYS_SPECIFIC_DATA *psSysSpecData, IMG_BOOL bTryLock)
-{
-        if (!in_interrupt())
-        {
-                if (bTryLock)
-                {
-                        int locked = mutex_trylock(&psSysSpecData->sPowerLock);
-                        if (locked == 0)
-                        {
-                                return PVRSRV_ERROR_RETRY;
-                        }
-                }
-                else
-                {
-                        mutex_lock(&psSysSpecData->sPowerLock);
-                }
-        }
-
-        return PVRSRV_OK;
-}
-
-static IMG_VOID PowerLockUnwrap(SYS_SPECIFIC_DATA *psSysSpecData)
-{
-        if (!in_interrupt())
-        {
-                mutex_unlock(&psSysSpecData->sPowerLock);
-        }
-}
-
-PVRSRV_ERROR SysPowerLockWrap(IMG_BOOL bTryLock)
-{
-        SYS_DATA        *psSysData;
-
-        SysAcquireData(&psSysData);
-
-        return PowerLockWrap(psSysData->pvSysSpecificData, bTryLock);
-}
-
-IMG_VOID SysPowerLockUnwrap(IMG_VOID)
-{
-        SYS_DATA        *psSysData;
-
-        SysAcquireData(&psSysData);
-
-        PowerLockUnwrap(psSysData->pvSysSpecificData);
-}
-
-
-IMG_BOOL WrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData)
-{
-       return IMG_TRUE;
-}
-
-IMG_VOID UnwrapSystemPowerChange(SYS_SPECIFIC_DATA *psSysSpecData)
-{
-}
-
-static inline IMG_UINT32 scale_by_rate(IMG_UINT32 val, IMG_UINT32 rate1, IMG_UINT32 rate2)
-{
-       if (rate1 >= rate2)
-       {
-               return val * (rate1 / rate2);
-       }
-
-       return val / (rate2 / rate1);
-}
-
-static inline IMG_UINT32 scale_prop_to_SGX_clock(IMG_UINT32 val, IMG_UINT32 rate)
-{
-       if(cpu_is_ti816x())
-       {
-               return scale_by_rate(val, rate, SYS_389x_SGX_CLOCK_SPEED);
-       }
-       else
-       {
-       
-               return scale_by_rate(val, rate, SYS_387x_SGX_CLOCK_SPEED);
-       }
-}
-
-static inline IMG_UINT32 scale_inv_prop_to_SGX_clock(IMG_UINT32 val, IMG_UINT32 rate)
-{
-       if(cpu_is_ti816x())
-       {
-               return scale_by_rate(val, SYS_389x_SGX_CLOCK_SPEED, rate);
-       }
-       else
-       {
-               return scale_by_rate(val, SYS_387x_SGX_CLOCK_SPEED, rate);
-       }
-}
-
-IMG_VOID SysGetSGXTimingInformation(SGX_TIMING_INFORMATION *psTimingInfo)
-{
-       IMG_UINT32 rate;
-
-#if defined(NO_HARDWARE)
-       if(cpu_is_ti816x())
-       {
-               rate = SYS_389x_SGX_CLOCK_SPEED;
-       }
-       else
-       {
-               rate = SYS_387x_SGX_CLOCK_SPEED;
-       }
-
-#else
-       PVR_ASSERT(atomic_read(&gpsSysSpecificData->sSGXClocksEnabled) != 0);
-
-       rate = clk_get_rate(gpsSysSpecificData->psSGX_FCK);
-       PVR_ASSERT(rate != 0);
-#endif
-       psTimingInfo->ui32CoreClockSpeed = rate;
-       psTimingInfo->ui32HWRecoveryFreq = scale_prop_to_SGX_clock(SYS_SGX_HWRECOVERY_TIMEOUT_FREQ, rate);
-       psTimingInfo->ui32uKernelFreq = scale_prop_to_SGX_clock(SYS_SGX_PDS_TIMER_FREQ, rate);
-#if defined(SUPPORT_ACTIVE_POWER_MANAGEMENT)
-       psTimingInfo->bEnableActivePM = IMG_TRUE;
-#else
-       psTimingInfo->bEnableActivePM = IMG_FALSE;
-#endif 
-       psTimingInfo->ui32ActivePowManLatencyms = SYS_SGX_ACTIVE_POWER_LATENCY_MS;
-}
-
-PVRSRV_ERROR EnableSGXClocks(SYS_DATA *psSysData)
-{
-#if !defined(NO_HARDWARE)
-       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
-/*
-       long lNewRate;
-       long lRate;
-*/
-       IMG_INT res;
-
-       
-       if (atomic_read(&psSysSpecData->sSGXClocksEnabled) != 0)
-       {
-               return PVRSRV_OK;
-       }
-
-       PVR_DPF((PVR_DBG_MESSAGE, "EnableSGXClocks: Enabling SGX Clocks"));
-
-#if defined(DEBUG)
-       {
-
-               IMG_UINT32 rate = clk_get_rate(psSysSpecData->psMPU_CK);
-               PVR_DPF((PVR_DBG_MESSAGE, "EnableSGXClocks: CPU Clock is %dMhz", HZ_TO_MHZ(rate)));
-       }
-#endif
-
-                res = clk_enable(psSysSpecData->psSGX_FCK);
-                if(res != 0)
-               {
-                        PVR_DPF((PVR_DBG_ERROR, "EnableSsystemClocks: Couldn't enable SGX Clock"));
-                        return PVRSRV_ERROR_UNABLE_TO_ENABLE_CLOCK;;
-               }
-//             else
-//             PVR_TRACE(("EnableSystemClocks: SGX clk_enable successful"));
-                
-//             res = clk_get_rate(psSysSpecData->psSGX_FCK);
-//              PVR_TRACE(("Default SGX clock rate is %dMHz", HZ_TO_MHZ(res)));
-
-                if(cpu_is_ti816x())
-                   res = clk_set_rate(psSysSpecData->psSGX_FCK,SYS_389x_SGX_CLOCK_SPEED);
-               else
-                    res = clk_set_rate(psSysSpecData->psSGX_FCK,SYS_387x_SGX_CLOCK_SPEED);
-                
-                if(res != 0)
-                {
-                        PVR_DPF((PVR_DBG_ERROR, "EnableSsystemClocks: Couldn't set SGX Functional Clock rate"));
-                        return PVRSRV_ERROR_UNABLE_TO_SET_CLOCK_RATE;
-                }
-                else
-                {
-                        res = clk_get_rate(psSysSpecData->psSGX_FCK);
-//                      PVR_TRACE(("SGX clock rate after set_clk_rate() is %dMHz", HZ_TO_MHZ(res)));
-                }
-/*
-       res = clk_enable(psSysSpecData->psSGX_FCK);
-       if (res < 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: Couldn't enable SGX functional clock (%d)", res));
-               return PVRSRV_ERROR_UNABLE_TO_ENABLE_CLOCK;
-       }
-*/
-/*
-       res = clk_enable(psSysSpecData->psSGX_ICK);
-       if (res < 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: Couldn't enable SGX interface clock (%d)", res));
-
-               clk_disable(psSysSpecData->psSGX_FCK);
-               return PVRSRV_ERROR_UNABLE_TO_ENABLE_CLOCK;
-       }
-
-       lNewRate = clk_round_rate(psSysSpecData->psSGX_FCK, SYS_SGX_CLOCK_SPEED + ONE_MHZ);
-       if (lNewRate <= 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSGXClocks: Couldn't round SGX functional clock rate"));
-               return PVRSRV_ERROR_UNABLE_TO_ROUND_CLOCK_RATE;
-       }
-
-       
-       lRate = clk_get_rate(psSysSpecData->psSGX_FCK);
-       if (lRate != lNewRate)
-       {
-               res = clk_set_rate(psSysSpecData->psSGX_FCK, lNewRate);
-               if (res < 0)
-               {
-                       PVR_DPF((PVR_DBG_WARNING, "EnableSGXClocks: Couldn't set SGX functional clock rate (%d)", res));
-               }
-       }
-*/
-#if defined(DEBUG)
-       {
-               IMG_UINT32 rate = clk_get_rate(psSysSpecData->psSGX_FCK);
-               PVR_DPF((PVR_DBG_MESSAGE, "EnableSGXClocks: SGX Functional Clock is %dMhz", HZ_TO_MHZ(rate)));
-       }
-#endif
-
-       
-       atomic_set(&psSysSpecData->sSGXClocksEnabled, 1);
-
-#else  
-       PVR_UNREFERENCED_PARAMETER(psSysData);
-#endif 
-       return PVRSRV_OK;
-}
-
-
-IMG_VOID DisableSGXClocks(SYS_DATA *psSysData)
-{
-#if !defined(NO_HARDWARE)
-       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
-
-       
-       if (atomic_read(&psSysSpecData->sSGXClocksEnabled) == 0)
-       {
-               return;
-       }
-
-       PVR_DPF((PVR_DBG_MESSAGE, "DisableSGXClocks: Disabling SGX Clocks"));
-
-/*     if (psSysSpecData->psSGX_ICK)
-       {
-               clk_disable(psSysSpecData->psSGX_ICK);
-       }
-*/
-       if (psSysSpecData->psSGX_FCK)
-       {
-               clk_disable(psSysSpecData->psSGX_FCK);
-       }
-
-       
-       atomic_set(&psSysSpecData->sSGXClocksEnabled, 0);
-
-#else  
-       PVR_UNREFERENCED_PARAMETER(psSysData);
-#endif 
-}
-
-PVRSRV_ERROR EnableSystemClocks(SYS_DATA *psSysData)
-{
-       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
-       struct clk *psCLK;
-//     IMG_INT res;
-//      IMG_BOOL bPowerLock;
-       PVRSRV_ERROR eError;
-
-#if defined(DEBUG) || defined(TIMING)
-        IMG_INT res;
-       IMG_INT rate;
-       struct clk *sys_ck;
-       IMG_CPU_PHYADDR     TimerRegPhysBase;
-       IMG_HANDLE hTimerEnable;
-       IMG_UINT32 *pui32TimerEnable;
-
-#endif 
-
-       PVR_TRACE(("EnableSystemClocks: Enabling System Clocks"));
-
-       if (!psSysSpecData->bSysClocksOneTimeInit)
-       {
-               mutex_init(&psSysSpecData->sPowerLock);
-
-               atomic_set(&psSysSpecData->sSGXClocksEnabled, 0);
-
-            //    if(cpu_is_ti816x())
-            //    {
-                  psCLK = clk_get(NULL, "sgx_ck");
-            //    } else {
-            //      psCLK = clk_get(NULL, "gfx_fck");
-            //    }
-               if (IS_ERR(psCLK))
-                {
-                        PVR_DPF((PVR_DBG_ERROR, "EnableSsystemClocks: Couldn't get SGX Functional Clock"));
-                        goto ExitError;
-                }
-                psSysSpecData->psSGX_FCK = psCLK;
-
-                psSysSpecData->bSysClocksOneTimeInit = IMG_TRUE;
-        }
-/*        else
-        {
-
-                bPowerLock = PowerLockWrappedOnCPU(psSysSpecData);
-                if (bPowerLock)
-                {
-                        PowerLockUnwrap(psSysSpecData);
-                }
-        }
-
-*/
-
-/*             
-                psCLK = clk_get(NULL, SGX_PARENT_CLOCK);
-               if (IS_ERR(psCLK))
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "EnableSsystemClocks: Couldn't get Core Clock"));
-                       goto ExitError;
-               }
-               psSysSpecData->psCORE_CK = psCLK;
-
-               psCLK = clk_get(NULL, "sgx_fck");
-               if (IS_ERR(psCLK))
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "EnableSsystemClocks: Couldn't get SGX Functional Clock"));
-                       goto ExitError;
-               }
-               psSysSpecData->psSGX_FCK = psCLK;
-
-               psCLK = clk_get(NULL, "sgx_ick");
-               if (IS_ERR(psCLK))
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't get SGX Interface Clock"));
-                       goto ExitError;
-               }
-               psSysSpecData->psSGX_ICK = psCLK;
-
-#if defined(DEBUG)
-               psCLK = clk_get(NULL, "mpu_ck");
-               if (IS_ERR(psCLK))
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't get MPU Clock"));
-                       goto ExitError;
-               }
-               psSysSpecData->psMPU_CK = psCLK;
-#endif
-               res = clk_set_parent(psSysSpecData->psSGX_FCK, psSysSpecData->psCORE_CK);
-               if (res < 0)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't set SGX parent clock (%d)", res));
-                       goto ExitError;
-               }
-
-               psSysSpecData->bSysClocksOneTimeInit = IMG_TRUE;
-       }
-*/
-#if defined(DEBUG) || defined(TIMING)
-        if(cpu_is_ti816x()) {
-                psCLK = clk_get(NULL, "gpt6_fck");
-        } else {
-                psCLK = clk_get(NULL, "gpt7_fck");
-        }
-       if (IS_ERR(psCLK))
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't get GPTIMER11 functional clock"));
-               goto ExitUnRegisterConstraintNotifications;
-       }
-       psSysSpecData->psGPT11_FCK = psCLK;
-
-        if(cpu_is_ti816x()) {
-                psCLK = clk_get(NULL, "gpt6_ick");
-        } else {
-                psCLK = clk_get(NULL, "gpt7_ick");
-        }
-       if (IS_ERR(psCLK))
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't get GPTIMER11 interface clock"));
-               goto ExitUnRegisterConstraintNotifications;
-       }
-       psSysSpecData->psGPT11_ICK = psCLK;
-/*
-       sys_ck = clk_get(NULL, "sys_ck");
-       if (IS_ERR(sys_ck))
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't get System clock"));
-               goto ExitUnRegisterConstraintNotifications;
-       }
-
-       if(clk_get_parent(psSysSpecData->psGPT11_FCK) != sys_ck)
-       {
-               PVR_TRACE(("Setting GPTIMER11 parent to System Clock"));
-               res = clk_set_parent(psSysSpecData->psGPT11_FCK, sys_ck);
-               if (res < 0)
-               {
-                       PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't set GPTIMER11 parent clock (%d)", res));
-               goto ExitUnRegisterConstraintNotifications;
-               }
-       }
-*/
-       rate = clk_get_rate(psSysSpecData->psGPT11_FCK);
-       PVR_TRACE(("GPTIMER11 clock is %dMHz", HZ_TO_MHZ(rate)));
-
-       res = clk_enable(psSysSpecData->psGPT11_FCK);
-       if (res < 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't enable GPTIMER11 functional clock (%d)", res));
-               goto ExitUnRegisterConstraintNotifications;
-       }
-
-       res = clk_enable(psSysSpecData->psGPT11_ICK);
-       if (res < 0)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: Couldn't enable GPTIMER11 interface clock (%d)", res));
-               goto ExitDisableGPT11FCK;
-       }
-
-       
-       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_TSICR_SYS_PHYS_BASE;
-       pui32TimerEnable = OSMapPhysToLin(TimerRegPhysBase,
-                  4,
-                  PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
-                  &hTimerEnable);
-
-       if (pui32TimerEnable == IMG_NULL)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: OSMapPhysToLin failed"));
-               goto ExitDisableGPT11ICK;
-       }
-
-       rate = *pui32TimerEnable;
-       if(!(rate & 4))
-       {
-               PVR_TRACE(("Setting GPTIMER11 mode to posted (currently is non-posted)"));
-
-               
-               *pui32TimerEnable = rate | 4;
-       }
-
-       OSUnMapPhysToLin(pui32TimerEnable,
-                   4,
-                   PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
-                   hTimerEnable);
-
-       
-       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_ENABLE_SYS_PHYS_BASE;
-       pui32TimerEnable = OSMapPhysToLin(TimerRegPhysBase,
-                  4,
-                  PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
-                  &hTimerEnable);
-
-       if (pui32TimerEnable == IMG_NULL)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "EnableSystemClocks: OSMapPhysToLin failed"));
-               goto ExitDisableGPT11ICK;
-       }
-
-       
-       *pui32TimerEnable = 3;
-
-       OSUnMapPhysToLin(pui32TimerEnable,
-                   4,
-                   PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
-                   hTimerEnable);
-
-#endif 
-
-       eError = PVRSRV_OK;
-       goto Exit;
-
-#if defined(DEBUG) || defined(TIMING)
-ExitDisableGPT11ICK:
-       clk_disable(psSysSpecData->psGPT11_ICK);
-ExitDisableGPT11FCK:
-       clk_disable(psSysSpecData->psGPT11_FCK);
-ExitUnRegisterConstraintNotifications:
-#endif 
-ExitError:
-       eError = PVRSRV_ERROR_DISABLE_CLOCK_FAILURE;
-Exit:
-       return eError;
-}
-
-IMG_VOID DisableSystemClocks(SYS_DATA *psSysData)
-{
-#if defined(DEBUG) || defined(TIMING)
-       SYS_SPECIFIC_DATA *psSysSpecData = (SYS_SPECIFIC_DATA *) psSysData->pvSysSpecificData;
-       IMG_CPU_PHYADDR TimerRegPhysBase;
-       IMG_HANDLE hTimerDisable;
-       IMG_UINT32 *pui32TimerDisable;
-#endif 
-
-       PVR_TRACE(("DisableSystemClocks: Disabling System Clocks"));
-
-       
-       DisableSGXClocks(psSysData);
-
-#if defined(DEBUG) || defined(TIMING)
-       
-       TimerRegPhysBase.uiAddr = SYS_TI81xx_GP7TIMER_ENABLE_SYS_PHYS_BASE;
-       pui32TimerDisable = OSMapPhysToLin(TimerRegPhysBase,
-                               4,
-                               PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
-                               &hTimerDisable);
-
-       if (pui32TimerDisable == IMG_NULL)
-       {
-               PVR_DPF((PVR_DBG_ERROR, "DisableSystemClocks: OSMapPhysToLin failed"));
-       }
-       else
-       {
-               *pui32TimerDisable = 0;
-
-               OSUnMapPhysToLin(pui32TimerDisable,
-                               4,
-                               PVRSRV_HAP_KERNEL_ONLY|PVRSRV_HAP_UNCACHED,
-                               hTimerDisable);
-       }
-
-       clk_disable(psSysSpecData->psGPT11_ICK);
-
-       clk_disable(psSysSpecData->psGPT11_FCK);
-
-#endif 
-}
index f1cb02a..d9fd825 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- **************************************************************************/
+/*************************************************************************/ /*!
+@File           linuxsrv.h
+@Title          Module defs for pvr core drivers.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _LINUXSRV_H__
 #define _LINUXSRV_H__
index f61107f..e1e8868 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 ccflags-y += \
        -I$(TOP)/tools/intern/debug/dbgdriv/common \
index 2991f6a..e050879 100644 (file)
@@ -1,27 +1,42 @@
-#
-# Copyright (C) Imagination Technologies Ltd. All rights reserved.
+########################################################################### ###
+#@Copyright     Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+#@License       Dual MIT/GPLv2
 # 
-# This program is free software; you can redistribute it and/or modify it
-# under the terms and conditions of the GNU General Public License,
-# version 2, as published by the Free Software Foundation.
+# The contents of this file are subject to the MIT license as set out below.
 # 
-# This program is distributed in the hope it will be useful but, except 
-# as otherwise stated in writing, without any warranty; without even the 
-# implied warranty of merchantability or fitness for a particular purpose. 
-# See the GNU General Public License for more details.
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to deal
+# in the Software without restriction, including without limitation the rights
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+# copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
 # 
-# You should have received a copy of the GNU General Public License along with
-# this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
 # 
-# The full GNU General Public License is included in this distribution in
-# the file called "COPYING".
-#
-# Contact Information:
-# Imagination Technologies Ltd. <gpl-support@imgtec.com>
-# Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
+# Alternatively, the contents of this file may be used under the terms of
+# the GNU General Public License Version 2 ("GPL") in which case the provisions
+# of GPL are applicable instead of those above.
 # 
-#
+# If you wish to allow use of your version of this file only under the terms of
+# GPL, and not to allow others to use your version of this file under the terms
+# of the MIT license, indicate your decision by deleting the provisions above
+# and replace them with the notice and other provisions required by GPL as set
+# out in the file called "GPL-COPYING" included in this distribution. If you do
+# not delete the provisions above, a recipient may use your version of this file
+# under the terms of either the MIT license or GPL.
+# 
+# This License is also included in this distribution in the file called
+# "MIT-COPYING".
+# 
+# EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+# PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+# BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+# PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+### ###########################################################################
 
 modules := dbgdrv
 
index 4bf93d0..0b8d445 100644 (file)
@@ -1,29 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Debug Driver
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    32 Bit kernel mode debug driver
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifdef LINUX
 #include <linux/string.h>
@@ -53,6 +68,9 @@ typedef struct _DBG_LASTFRAME_BUFFER_
        struct _DBG_LASTFRAME_BUFFER_   *psNext;
 } *PDBG_LASTFRAME_BUFFER;
 
+/******************************************************************************
+ Global vars
+******************************************************************************/
 
 static PDBG_STREAM     g_psStreamList = 0;
 static PDBG_LASTFRAME_BUFFER   g_psLFBufferList;
@@ -78,6 +96,9 @@ IMG_UINT32 SpaceInStream(PDBG_STREAM psStream);
 IMG_BOOL ExpandStreamBuffer(PDBG_STREAM psStream, IMG_UINT32 ui32NewSize);
 PDBG_LASTFRAME_BUFFER FindLFBuf(PDBG_STREAM psStream);
 
+/***************************************************************************
+ Declare kernel mode service table.
+***************************************************************************/
 DBGKM_SERVICE_TABLE g_sDBGKMServices =
 {
        sizeof (DBGKM_SERVICE_TABLE),
@@ -114,53 +135,74 @@ DBGKM_SERVICE_TABLE g_sDBGKMServices =
 };
 
 
+/* Static function declarations */
 static IMG_UINT32 DBGDrivWritePersist(PDBG_STREAM psMainStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level);
 static IMG_VOID InvalidateAllStreams(IMG_VOID);
 
+/*****************************************************************************
+ Code
+*****************************************************************************/
 
 
 
 DBGKM_CONNECT_NOTIFIER g_fnDBGKMNotifier;
 
+/*!
+ @name         ExtDBGDrivSetConnectNotifier
+ @brief                Registers one or more services callback functions which are called on events in the dbg driver
+ @param                fn_notifier - services callbacks
+ @return       none
+ */
 IMG_VOID IMG_CALLCONV ExtDBGDrivSetConnectNotifier(DBGKM_CONNECT_NOTIFIER fn_notifier)
 {
-       
+       /* Set the callback function which enables the debug driver to
+        * communicate to services KM when pdump is connected.
+        */
        g_fnDBGKMNotifier = fn_notifier;
 }
 
+/*!
+ @name ExtDBGDrivCreateStream
+ */
 IMG_VOID * IMG_CALLCONV ExtDBGDrivCreateStream(IMG_CHAR *      pszName, IMG_UINT32 ui32CapMode, IMG_UINT32     ui32OutMode, IMG_UINT32 ui32Flags, IMG_UINT32 ui32Size)
 {
        IMG_VOID *      pvRet;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        pvRet=DBGDrivCreateStream(pszName, ui32CapMode, ui32OutMode, ui32Flags, ui32Size);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return pvRet;
 }
 
+/*!
+ @name ExtDBGDrivDestroyStream
+ */
 void IMG_CALLCONV ExtDBGDrivDestroyStream(PDBG_STREAM psStream)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivDestroyStream(psStream);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivFindStream
+ */
 IMG_VOID * IMG_CALLCONV ExtDBGDrivFindStream(IMG_CHAR * pszName, IMG_BOOL bResetStream)
 {
        IMG_VOID *      pvRet;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        pvRet=DBGDrivFindStream(pszName, bResetStream);
@@ -173,215 +215,260 @@ IMG_VOID * IMG_CALLCONV ExtDBGDrivFindStream(IMG_CHAR * pszName, IMG_BOOL bReset
                PVR_DPF((PVR_DBG_ERROR, "pfnConnectNotifier not initialised.\n"));
        }               
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return pvRet;
 }
 
+/*!
+ @name ExtDBGDrivWriteString
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszString,IMG_UINT32 ui32Level)
 {
        IMG_UINT32      ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret=DBGDrivWriteString(psStream, pszString, ui32Level);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivReadString
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivReadString(PDBG_STREAM psStream,IMG_CHAR * pszString,IMG_UINT32 ui32Limit)
 {
        IMG_UINT32 ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret=DBGDrivReadString(psStream, pszString, ui32Limit);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivWrite
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivWrite(PDBG_STREAM psStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level)
 {
        IMG_UINT32      ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret=DBGDrivWrite(psStream, pui8InBuf, ui32InBuffSize, ui32Level);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivRead
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivRead(PDBG_STREAM psStream, IMG_BOOL bReadInitBuffer, IMG_UINT32 ui32OutBuffSize,IMG_UINT8 * pui8OutBuf)
 {
        IMG_UINT32 ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret=DBGDrivRead(psStream, bReadInitBuffer, ui32OutBuffSize, pui8OutBuf);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivSetCaptureMode
+ */
 void IMG_CALLCONV ExtDBGDrivSetCaptureMode(PDBG_STREAM psStream,IMG_UINT32 ui32Mode,IMG_UINT32 ui32Start,IMG_UINT32 ui32End,IMG_UINT32 ui32SampleRate)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivSetCaptureMode(psStream, ui32Mode, ui32Start, ui32End, ui32SampleRate);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivSetOutputMode
+ */
 void IMG_CALLCONV ExtDBGDrivSetOutputMode(PDBG_STREAM psStream,IMG_UINT32 ui32OutMode)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivSetOutputMode(psStream, ui32OutMode);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivSetDebugLevel
+ */
 void IMG_CALLCONV ExtDBGDrivSetDebugLevel(PDBG_STREAM psStream,IMG_UINT32 ui32DebugLevel)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivSetDebugLevel(psStream, ui32DebugLevel);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivSetFrame
+ */
 void IMG_CALLCONV ExtDBGDrivSetFrame(PDBG_STREAM psStream,IMG_UINT32 ui32Frame)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivSetFrame(psStream, ui32Frame);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivGetFrame
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivGetFrame(PDBG_STREAM psStream)
 {
        IMG_UINT32      ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret=DBGDrivGetFrame(psStream);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivIsLastCaptureFrame
+ */
 IMG_BOOL IMG_CALLCONV ExtDBGDrivIsLastCaptureFrame(PDBG_STREAM psStream)
 {
        IMG_BOOL        bRet;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        bRet = DBGDrivIsLastCaptureFrame(psStream);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return bRet;
 }
 
+/*!
+ @name ExtDBGDrivIsCaptureFrame
+ */
 IMG_BOOL IMG_CALLCONV ExtDBGDrivIsCaptureFrame(PDBG_STREAM psStream, IMG_BOOL bCheckPreviousFrame)
 {
        IMG_BOOL        bRet;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        bRet = DBGDrivIsCaptureFrame(psStream, bCheckPreviousFrame);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return bRet;
 }
 
+/*!
+ @name ExtDBGDrivOverrideMode
+ */
 void IMG_CALLCONV ExtDBGDrivOverrideMode(PDBG_STREAM psStream,IMG_UINT32 ui32Mode)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivOverrideMode(psStream, ui32Mode);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivDefaultMode
+ */
 void IMG_CALLCONV ExtDBGDrivDefaultMode(PDBG_STREAM psStream)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivDefaultMode(psStream);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivWrite2
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivWrite2(PDBG_STREAM psStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level)
 {
        IMG_UINT32      ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret=DBGDrivWrite2(psStream, pui8InBuf, ui32InBuffSize, ui32Level);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivWritePersist
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivWritePersist(PDBG_STREAM psStream,IMG_UINT8 *pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level)
 {
        IMG_UINT32      ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret=DBGDrivWritePersist(psStream, pui8InBuf, ui32InBuffSize, ui32Level);
@@ -390,162 +477,202 @@ IMG_UINT32 IMG_CALLCONV ExtDBGDrivWritePersist(PDBG_STREAM psStream,IMG_UINT8 *p
                PVR_DPF((PVR_DBG_ERROR, "An error occurred in DBGDrivWritePersist."));
        }
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivWriteStringCM
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivWriteStringCM(PDBG_STREAM psStream,IMG_CHAR * pszString,IMG_UINT32 ui32Level)
 {
        IMG_UINT32      ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret=DBGDrivWriteStringCM(psStream, pszString, ui32Level);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivWriteCM
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivWriteCM(PDBG_STREAM psStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level)
 {
        IMG_UINT32      ui32Ret;
        
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
        
        ui32Ret=DBGDrivWriteCM(psStream, pui8InBuf, ui32InBuffSize, ui32Level);
        
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
        
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivSetMarker
+ */
 void IMG_CALLCONV ExtDBGDrivSetMarker(PDBG_STREAM psStream, IMG_UINT32 ui32Marker)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivSetMarker(psStream, ui32Marker);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivGetMarker
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivGetMarker(PDBG_STREAM psStream)
 {
        IMG_UINT32      ui32Marker;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Marker = DBGDrivGetMarker(psStream);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Marker;
 }
 
+/*!
+ @name ExtDBGDrivWriteLF
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivWriteLF(PDBG_STREAM psStream, IMG_UINT8 * pui8InBuf, IMG_UINT32 ui32InBuffSize, IMG_UINT32 ui32Level, IMG_UINT32 ui32Flags)
 {
        IMG_UINT32      ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret = DBGDrivWriteLF(psStream, pui8InBuf, ui32InBuffSize, ui32Level, ui32Flags);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivReadLF
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivReadLF(PDBG_STREAM psStream, IMG_UINT32 ui32OutBuffSize, IMG_UINT8 * pui8OutBuf)
 {
        IMG_UINT32 ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret = DBGDrivReadLF(psStream, ui32OutBuffSize, pui8OutBuf);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
 
+/*!
+ @name ExtDBGDrivStartInitPhase
+ */
 IMG_VOID IMG_CALLCONV ExtDBGDrivStartInitPhase(PDBG_STREAM psStream)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivStartInitPhase(psStream);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivStopInitPhase
+ */
 IMG_VOID IMG_CALLCONV ExtDBGDrivStopInitPhase(PDBG_STREAM psStream)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivStopInitPhase(psStream);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return;
 }
 
+/*!
+ @name ExtDBGDrivGetStreamOffset
+ */
 IMG_UINT32 IMG_CALLCONV ExtDBGDrivGetStreamOffset(PDBG_STREAM psStream)
 {
        IMG_UINT32 ui32Ret;
 
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        ui32Ret = DBGDrivGetStreamOffset(psStream);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 
        return ui32Ret;
 }
 
+/*!
+ @name ExtDBGDrivSetStreamOffset
+ */
 IMG_VOID IMG_CALLCONV ExtDBGDrivSetStreamOffset(PDBG_STREAM psStream, IMG_UINT32 ui32StreamOffset)
 {
-       
+       /* Aquire API Mutex */
        HostAquireMutex(g_pvAPIMutex);
 
        DBGDrivSetStreamOffset(psStream, ui32StreamOffset);
 
-       
+       /* Release API Mutex */
        HostReleaseMutex(g_pvAPIMutex);
 }
 
+/*!
+ @name ExtDBGDrivWaitForEvent
+ */
 IMG_VOID IMG_CALLCONV ExtDBGDrivWaitForEvent(DBG_EVENT eEvent)
 {
 #if defined(SUPPORT_DBGDRV_EVENT_OBJECTS)
        DBGDrivWaitForEvent(eEvent);
-#else  
-       PVR_UNREFERENCED_PARAMETER(eEvent);                             
-#endif 
-}
-
+#else  /* defined(SUPPORT_DBGDRV_EVENT_OBJECTS) */
+       PVR_UNREFERENCED_PARAMETER(eEvent);                             /* PRQA S 3358 */
+#endif /* defined(SUPPORT_DBGDRV_EVENT_OBJECTS) */
+}
+
+/*!****************************************************************************
+ @name         AtoI
+ @brief                Returns the integer value of a decimal string
+ @param                szIn - String with hexadecimal value
+ @return       IMG_UINT32 integer value, 0 if string is null or not valid
+                               Based on Max`s one, now copes with (only) hex ui32ords, upper or lower case a-f.
+*****************************************************************************/
 IMG_UINT32 AtoI(IMG_CHAR *szIn)
 {
        IMG_INT         iLen = 0;
@@ -555,19 +682,19 @@ IMG_UINT32 AtoI(IMG_CHAR *szIn)
        IMG_INT         iPos;
        IMG_CHAR        bc;
 
-       
+       //get len of string
        while (szIn[iLen] > 0)
        {
                iLen ++;
        }
 
-       
+       //nothing to do
        if (iLen == 0)
        {
                return (0);
        }
 
-       
+       /* See if we have an 'x' or 'X' before the number to make it a hex number */
        iPos=0;
        while (szIn[iPos] == '0')
        {
@@ -583,22 +710,22 @@ IMG_UINT32 AtoI(IMG_CHAR *szIn)
                szIn[iPos]='0';
        }
 
-       
+       //go through string from right (least significant) to left
        for (iPos = iLen - 1; iPos >= 0; iPos --)
        {
                bc = szIn[iPos];
 
-               if ( (bc >= 'a') && (bc <= 'f') && ui32Base == 16)                      
+               if ( (bc >= 'a') && (bc <= 'f') && ui32Base == 16)                      //handle lower case a-f
                {
                        bc -= 'a' - 0xa;
                }
                else
-               if ( (bc >= 'A') && (bc <= 'F') && ui32Base == 16)                      
+               if ( (bc >= 'A') && (bc <= 'F') && ui32Base == 16)                      //handle upper case A-F
                {
                        bc -= 'A' - 0xa;
                }
                else
-               if ((bc >= '0') && (bc <= '9'))                         
+               if ((bc >= '0') && (bc <= '9'))                         //if char out of range, return 0
                {
                        bc -= '0';
                }
@@ -613,6 +740,12 @@ IMG_UINT32 AtoI(IMG_CHAR *szIn)
 }
 
 
+/*!****************************************************************************
+ @name         StreamValid
+ @brief                Validates supplied debug buffer.
+ @param                psStream - debug stream
+ @return       true if valid
+*****************************************************************************/
 static IMG_BOOL StreamValid(PDBG_STREAM psStream)
 {
        PDBG_STREAM     psThis;
@@ -635,6 +768,12 @@ static IMG_BOOL StreamValid(PDBG_STREAM psStream)
 }
 
 
+/*!****************************************************************************
+ @name         StreamValidForRead
+ @brief                Validates supplied debug buffer for read op.
+ @param                psStream - debug stream
+ @return       true if readable
+*****************************************************************************/
 static IMG_BOOL StreamValidForRead(PDBG_STREAM psStream)
 {
        if( StreamValid(psStream) &&
@@ -646,6 +785,12 @@ static IMG_BOOL StreamValidForRead(PDBG_STREAM psStream)
        return(IMG_FALSE);
 }
 
+/*!****************************************************************************
+ @name         StreamValidForWrite
+ @brief                Validates supplied debug buffer for write op.
+ @param                psStream - debug stream
+ @return       true if writable
+*****************************************************************************/
 static IMG_BOOL StreamValidForWrite(PDBG_STREAM psStream)
 {
        if( StreamValid(psStream) &&
@@ -658,36 +803,45 @@ static IMG_BOOL StreamValidForWrite(PDBG_STREAM psStream)
 }
 
 
+/*!****************************************************************************
+ @name         Write
+ @brief                Copies data from a buffer into selected stream. Stream size is fixed.
+ @param                psStream - stream for output
+ @param                pui8Data - input buffer
+ @param                ui32InBuffSize - size of input
+ @return       none
+*****************************************************************************/
 static void Write(PDBG_STREAM psStream,IMG_PUINT8 pui8Data,IMG_UINT32 ui32InBuffSize)
 {
-       
-
+       /*
+               Split copy into two bits as necessary (if we're allowed to wrap).
+       */
        if (!psStream->bCircularAllowed)
        {
-               
+               //PVR_ASSERT( (psStream->ui32WPtr + ui32InBuffSize) < psStream->ui32Size );
        }
 
        if ((psStream->ui32WPtr + ui32InBuffSize) > psStream->ui32Size)
        {
-               
+               /* Yes we need two bits, calculate their sizes */
                IMG_UINT32 ui32B1 = psStream->ui32Size - psStream->ui32WPtr;
                IMG_UINT32 ui32B2 = ui32InBuffSize - ui32B1;
 
-               
+               /* Copy first block to current location */
                HostMemCopy((IMG_PVOID)((IMG_UINTPTR_T)psStream->pvBase + psStream->ui32WPtr),
                                (IMG_PVOID) pui8Data,
                                ui32B1);
 
-               
+               /* Copy second block to start of buffer */
                HostMemCopy(psStream->pvBase,
                                (IMG_PVOID)(pui8Data + ui32B1),
                                ui32B2);
 
-               
+               /* Set pointer to be the new end point */
                psStream->ui32WPtr = ui32B2;
        }
        else
-       {       
+       {       /* Can fit block in single chunk */
                HostMemCopy((IMG_PVOID)((IMG_UINTPTR_T)psStream->pvBase + psStream->ui32WPtr),
                                (IMG_PVOID) pui8Data,
                                ui32InBuffSize);
@@ -703,6 +857,13 @@ static void Write(PDBG_STREAM psStream,IMG_PUINT8 pui8Data,IMG_UINT32 ui32InBuff
 }
 
 
+/*!****************************************************************************
+ @name         MonoOut
+ @brief                Output data to mono display. [Possibly deprecated]
+ @param                pszString - input
+ @param                bNewLine - line wrapping
+ @return       none
+*****************************************************************************/
 void MonoOut(IMG_CHAR * pszString,IMG_BOOL bNewLine)
 {
 #if defined (_WIN64)
@@ -717,8 +878,9 @@ void MonoOut(IMG_CHAR * pszString,IMG_BOOL bNewLine)
 
        pScreen += g_ui32Line * 160;
 
-       
-
+       /*
+               Write the string.
+       */
        i=0;
        do
        {
@@ -736,8 +898,9 @@ void MonoOut(IMG_CHAR * pszString,IMG_BOOL bNewLine)
                g_ui32Line++;
        }
 
-       
-
+       /*
+               Scroll if necssary.
+       */
        if (g_ui32Line == g_ui32MonoLines)
        {
                g_ui32Line = g_ui32MonoLines - 1;
@@ -749,29 +912,41 @@ void MonoOut(IMG_CHAR * pszString,IMG_BOOL bNewLine)
 #endif 
 }
 
+/*!****************************************************************************
+ @name         WriteExpandingBuffer
+ @brief                Copies data from a buffer into selected stream. Stream size may be expandable.
+ @param                psStream - stream for output
+ @param                pui8InBuf - input buffer
+ @param                ui32InBuffSize - size of input
+ @return       bytes copied
+*****************************************************************************/
 static IMG_UINT32 WriteExpandingBuffer(PDBG_STREAM psStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize)
 {
        IMG_UINT ui32Space;
 
-       
-
+       /*
+               How much space have we got in the buffer ?
+       */
        ui32Space = SpaceInStream(psStream);
 
-       
-
+       /*
+               Don't copy anything if we don't have space or buffers not enabled.
+       */
        if ((psStream->psCtrl->ui32OutMode & DEBUG_OUTMODE_STREAMENABLE) == 0)
        {
                PVR_DPF((PVR_DBG_ERROR, "WriteExpandingBuffer: buffer %x is disabled", (IMG_UINTPTR_T) psStream));
                return(0);
        }
 
-       
-
+       /*
+               Check if we can expand the buffer 
+       */
        if (psStream->psCtrl->ui32Flags & DEBUG_FLAGS_NO_BUF_EXPANDSION)
        {
-               
-
-
+               /*
+                       Don't do anything if we've got less that 32 ui8tes of space and
+                       we're not allowing expansion of buffer space...
+               */
                if (ui32Space < 32)
                {
                        PVR_DPF((PVR_DBG_ERROR, "WriteExpandingBuffer: buffer %x is full and isn't expandable", (IMG_UINTPTR_T) psStream));
@@ -784,8 +959,9 @@ static IMG_UINT32 WriteExpandingBuffer(PDBG_STREAM psStream,IMG_UINT8 * pui8InBu
                {
                        IMG_UINT32      ui32NewBufSize;
 
-                       
-
+                       /*
+                               Find new buffer size 
+                       */
                        ui32NewBufSize = 2 * psStream->ui32Size;
 
                        PVR_DPF((PVR_DBGDRIV_MESSAGE, "Expanding buffer size = %x, new size = %x",
@@ -796,8 +972,9 @@ static IMG_UINT32 WriteExpandingBuffer(PDBG_STREAM psStream,IMG_UINT8 * pui8InBu
                                ui32NewBufSize += ui32InBuffSize;
                        }
 
-                       
-
+                       /* 
+                               Attempt to expand the buffer 
+                       */
                        if (!ExpandStreamBuffer(psStream,ui32NewBufSize))
                        {
                                if (ui32Space < 32)
@@ -808,7 +985,7 @@ static IMG_UINT32 WriteExpandingBuffer(PDBG_STREAM psStream,IMG_UINT8 * pui8InBu
                                        }
                                        else
                                        {
-                                               
+                                               /* out of memory */
                                                PVR_DPF((PVR_DBG_ERROR, "WriteExpandingBuffer: Unable to expand %x. Out of memory.", (IMG_UINTPTR_T) psStream));
                                                InvalidateAllStreams();
                                                return (0xFFFFFFFFUL);
@@ -816,23 +993,26 @@ static IMG_UINT32 WriteExpandingBuffer(PDBG_STREAM psStream,IMG_UINT8 * pui8InBu
                                }
                        }
 
-                       
-
+                       /* 
+                               Recalc the space in the buffer 
+                       */
                        ui32Space = SpaceInStream(psStream);
                        PVR_DPF((PVR_DBGDRIV_MESSAGE, "Expanded buffer, free space = %x",
                                        ui32Space));
                }
        }
 
-       
-
+       /*
+               Only copy what we can..
+       */
        if (ui32Space <= (ui32InBuffSize + 4))
        {
                ui32InBuffSize = ui32Space - 4;
        }
 
-       
-
+       /*
+               Write the stuff...
+       */
        Write(psStream,pui8InBuf,ui32InBuffSize);
 
 #if defined(SUPPORT_DBGDRV_EVENT_OBJECTS)
@@ -844,6 +1024,24 @@ static IMG_UINT32 WriteExpandingBuffer(PDBG_STREAM psStream,IMG_UINT8 * pui8InBu
        return(ui32InBuffSize);
 }
 
+/*****************************************************************************
+******************************************************************************
+******************************************************************************
+ THE ACTUAL FUNCTIONS
+******************************************************************************
+******************************************************************************
+*****************************************************************************/
+
+/*!****************************************************************************
+ @name         DBGDrivCreateStream
+ @brief                Creates a pdump/debug stream
+ @param                pszName - stream name
+ @param                ui32CapMode - capture mode (framed, continuous, hotkey)
+ @param                ui32OutMode - output mode (see dbgdrvif.h)
+ @param                ui32Flags - output flags, text stream bit is set for pdumping
+ @param                ui32Size - size of stream buffer in pages
+ @return       none
+*****************************************************************************/
 IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *         pszName,
                                                                   IMG_UINT32   ui32CapMode,
                                                                   IMG_UINT32   ui32OutMode,
@@ -859,9 +1057,10 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *            pszName,
        static IMG_CHAR pszNameInitSuffix[] = "_Init";
        IMG_UINT32              ui32OffSuffix;
 
-       
-
-
+       /*
+               If we already have a buffer using this name just return
+               its handle.
+       */
        psStream = (PDBG_STREAM) DBGDrivFindStream(pszName, IMG_FALSE);
 
        if (psStream)
@@ -869,8 +1068,9 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *             pszName,
                return ((IMG_VOID *) psStream);
        }
 
-       
-
+       /*
+               Allocate memory for control structures
+       */
        psStream = HostNonPageablePageAlloc(1);
        psInitStream = HostNonPageablePageAlloc(1);
        psLFBuffer = HostNonPageablePageAlloc(1);
@@ -886,7 +1086,7 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *             pszName,
                return((IMG_VOID *) 0);
        }
 
-       
+       /* Allocate memory for buffer */
        if ((ui32Flags & DEBUG_FLAGS_USE_NONPAGED_MEM) != 0)
        {
                pvBase = HostNonPageablePageAlloc(ui32Size);
@@ -903,7 +1103,7 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *             pszName,
                return((IMG_VOID *) 0);
        }
 
-       
+       /* Setup control state */
        psCtrl->ui32Flags = ui32Flags;
        psCtrl->ui32CapMode = ui32CapMode;
        psCtrl->ui32OutMode = ui32OutMode;
@@ -915,8 +1115,9 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *             pszName,
        psCtrl->ui32SampleRate = 1;
        psCtrl->bInitPhaseComplete = IMG_FALSE;
 
-       
-
+       /*
+               Setup internal debug buffer state.
+       */
        psStream->psNext = 0;
        psStream->pvBase = pvBase;
        psStream->psCtrl = psCtrl;
@@ -927,10 +1128,8 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *            pszName,
        psStream->ui32Marker = 0;
        psStream->bCircularAllowed = IMG_TRUE;
        psStream->ui32InitPhaseWOff = 0;
-       
-
 
-       
+       /* Allocate memory for buffer */
        if ((ui32Flags & DEBUG_FLAGS_USE_NONPAGED_MEM) != 0)
        {
                pvBase = HostNonPageablePageAlloc(ui32Size);
@@ -956,7 +1155,7 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *             pszName,
                return((IMG_VOID *) 0);
        }
 
-       
+       /* Initialise the stream for the init phase */
        psInitStream->psNext = 0;
        psInitStream->pvBase = pvBase;
        psInitStream->psCtrl = psCtrl;
@@ -967,12 +1166,9 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *            pszName,
        psInitStream->ui32Marker = 0;
        psInitStream->bCircularAllowed = IMG_FALSE;
        psInitStream->ui32InitPhaseWOff = 0;
-       
-
-
        psStream->psInitStream = psInitStream;
 
-       
+       /* Setup last frame buffer */
        psLFBuffer->psStream = psStream;
        psLFBuffer->ui32BufLen = 0UL;
 
@@ -980,8 +1176,9 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *             pszName,
        g_ui32HotkeyMiddumpStart = 0xffffffffUL;
        g_ui32HotkeyMiddumpEnd = 0xffffffffUL;
 
-       
-
+       /*
+               Copy buffer name.
+       */
        ui32Off = 0;
 
        do
@@ -991,10 +1188,11 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *           pszName,
                ui32Off++;
        }
        while ((pszName[ui32Off] != 0) && (ui32Off < (4096UL - sizeof(DBG_STREAM))));
-       psStream->szName[ui32Off] = pszName[ui32Off];   
-
-       
+       psStream->szName[ui32Off] = pszName[ui32Off];   /* PRQA S 3689 */
 
+       /*
+               Append suffix to init phase name
+       */
        ui32OffSuffix = 0;
        do
        {
@@ -1004,10 +1202,11 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *          pszName,
        }
        while ( (pszNameInitSuffix[ui32OffSuffix] != 0) &&
                        (ui32Off < (4096UL - sizeof(DBG_STREAM))));
-       psInitStream->szName[ui32Off] = pszNameInitSuffix[ui32OffSuffix];       
-
-       
+       psInitStream->szName[ui32Off] = pszNameInitSuffix[ui32OffSuffix];       /* PRQA S 3689 */
 
+       /*
+               Insert into list.
+       */
        psStream->psNext = g_psStreamList;
        g_psStreamList = psStream;
 
@@ -1019,6 +1218,12 @@ IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *           pszName,
        return((IMG_VOID *) psStream);
 }
 
+/*!****************************************************************************
+ @name         DBGDrivDestroyStream
+ @brief                Delete a stream and free its memory
+ @param                psStream - stream to be removed
+ @return       none
+*****************************************************************************/
 void IMG_CALLCONV DBGDrivDestroyStream(PDBG_STREAM psStream)
 {
        PDBG_STREAM     psStreamThis;
@@ -1029,8 +1234,9 @@ void IMG_CALLCONV DBGDrivDestroyStream(PDBG_STREAM psStream)
 
        PVR_DPF((PVR_DBG_MESSAGE, "DBGDriv: Destroying stream %s\r\n", psStream->szName ));
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -1040,8 +1246,9 @@ void IMG_CALLCONV DBGDrivDestroyStream(PDBG_STREAM psStream)
        
        psLFBuffer = FindLFBuf(psStream);
 
-       
-
+       /*
+               Remove from linked list.
+       */
        psStreamThis = g_psStreamList;
        psStreamPrev = 0;
 
@@ -1091,15 +1298,17 @@ void IMG_CALLCONV DBGDrivDestroyStream(PDBG_STREAM psStream)
                        psLFThis = psLFThis->psNext;
                }
        }
-       
-
+       /*
+               Dectivate hotkey it the stream is of this type.
+       */
        if (psStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_HOTKEY)
        {
                DeactivateHotKeys();
        }
 
-       
-
+       /*
+               And free its memory.
+       */
        if ((psStream->psCtrl->ui32Flags & DEBUG_FLAGS_USE_NONPAGED_MEM) != 0)
        {
                HostNonPageablePageFree(psStream->psCtrl);
@@ -1125,6 +1334,13 @@ void IMG_CALLCONV DBGDrivDestroyStream(PDBG_STREAM psStream)
        return;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivFindStream
+ @brief                Finds/resets a named stream
+ @param                pszName - stream name
+ @param                bResetStream - whether to reset the stream, e.g. to end pdump init phase
+ @return       none
+*****************************************************************************/
 IMG_VOID * IMG_CALLCONV DBGDrivFindStream(IMG_CHAR * pszName, IMG_BOOL bResetStream)
 {
        PDBG_STREAM     psStream;
@@ -1138,8 +1354,9 @@ IMG_VOID * IMG_CALLCONV DBGDrivFindStream(IMG_CHAR * pszName, IMG_BOOL bResetStr
                        pszName,
                        (bResetStream == IMG_TRUE) ? "with reset" : "no reset"));
 
-       
-
+       /*
+               Scan buffer names for supplied one.
+       */
        for (psThis = g_psStreamList; psThis != IMG_NULL; psThis = psThis->psNext)
        {
                bAreSame = IMG_TRUE;
@@ -1186,8 +1403,7 @@ IMG_VOID * IMG_CALLCONV DBGDrivFindStream(IMG_CHAR * pszName, IMG_BOOL bResetStr
                }
 
                {
-                       
-                       
+                       /* mark init stream to prevent further reading by pdump client */
                        psStream->psInitStream->ui32InitPhaseWOff = psStream->psInitStream->ui32WPtr;
                        PVR_DPF((PVR_DBGDRIV_MESSAGE, "Set %s client marker bo %x, total bw %x",
                                        psStream->szName,
@@ -1209,17 +1425,19 @@ static void IMG_CALLCONV DBGDrivInvalidateStream(PDBG_STREAM psStream)
        
        PVR_DPF((PVR_DBG_ERROR, "DBGDrivInvalidateStream: An error occurred for stream %s\r\n", psStream->szName ));
 
-       
-
-       
-
-
-
-
-       
+       /*
+               Validate buffer.
+       */
+       /*
+       if (!StreamValid(psStream))
+       {
+               return;
+       }
+*/
+       /* Write what we can of the error message */
        ui32Space = SpaceInStream(psStream);
 
-       
+       /* Make sure there's space for termination character */
        if(ui32Space > 0)
        {
                ui32Space--;
@@ -1238,10 +1456,15 @@ static void IMG_CALLCONV DBGDrivInvalidateStream(PDBG_STREAM psStream)
        pui8Buffer[ui32WPtr++] = '\0';
        psStream->ui32WPtr = ui32WPtr;
 
-       
+       /* Buffer will accept no more params from Services/client driver */
        psStream->psCtrl->ui32Flags |= DEBUG_FLAGS_READONLY;
 }
 
+/*!****************************************************************************
+ @name         InvalidateAllStreams
+ @brief                invalidate all streams in list
+ @return       none
+*****************************************************************************/
 static IMG_VOID InvalidateAllStreams(IMG_VOID)
 {
        PDBG_STREAM psStream = g_psStreamList;
@@ -1255,17 +1478,26 @@ static IMG_VOID InvalidateAllStreams(IMG_VOID)
 
 
 
+/*!****************************************************************************
+ @name         DBGDrivWriteStringCM
+ @brief                Write capture mode data, wraps DBGDrivWriteString
+ @param                psStream - stream
+ @param                pszString - input buffer
+ @param                ui32Level - debug level
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivWriteStringCM(PDBG_STREAM psStream,IMG_CHAR * pszString,IMG_UINT32 ui32Level)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForWrite(psStream))
        {
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               Only write string if debug capture mode adds up...
+       */
        if (psStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_FRAMED)
        {
                if      ((psStream->psCtrl->ui32Flags & DEBUG_FLAGS_ENABLESAMPLE) == 0)
@@ -1288,6 +1520,16 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteStringCM(PDBG_STREAM psStream,IMG_CHAR * psz
 
 }
 
+/*!****************************************************************************
+ @name         DBGDrivWriteString
+ @brief                Write string to stream (note stream buffer size is assumed fixed)
+ @param                psStream - stream
+ @param                pszString - string to write
+ @param                ui32Level - verbosity level
+ @return       -1; invalid stream
+                       0;      other error (e.g. stream not enabled)
+                       else number of characters written
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszString,IMG_UINT32 ui32Level)
 {
        IMG_UINT32      ui32Len;
@@ -1295,23 +1537,26 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszSt
        IMG_UINT32      ui32WPtr;
        IMG_UINT8 *     pui8Buffer;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForWrite(psStream))
        {
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               Check debug level.
+       */
        if ((psStream->psCtrl->ui32DebugLevel & ui32Level) == 0)
        {
                return(0xFFFFFFFFUL);
        }
 
-       
-
-
+       /*
+               Output to standard debug out ? (don't if async out
+               flag is set).
+       */
        if ((psStream->psCtrl->ui32OutMode & DEBUG_OUTMODE_ASYNC) == 0)
        {
                if (psStream->psCtrl->ui32OutMode & DEBUG_OUTMODE_STANDARDDBG)
@@ -1319,8 +1564,9 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszSt
                        PVR_DPF((PVR_DBG_MESSAGE,"%s: %s\r\n",psStream->szName, pszString));
                }
 
-               
-
+               /*
+                       Output to mono monitor ?
+               */
                if (psStream->psCtrl->ui32OutMode & DEBUG_OUTMODE_MONO)
                {
                        MonoOut(psStream->szName,IMG_FALSE);
@@ -1329,8 +1575,9 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszSt
                }
        }
 
-       
-
+       /*
+               Don't bother writing the string if it's not flagged
+       */
        if      (
                        !(
                                ((psStream->psCtrl->ui32OutMode & DEBUG_OUTMODE_STREAMENABLE) != 0) ||
@@ -1341,11 +1588,12 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszSt
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               How much space have we got in the buffer ?
+       */
        ui32Space=SpaceInStream(psStream);
 
-       
+       /* Make sure there's space for termination character */
        if(ui32Space > 0)
        {
                ui32Space--;
@@ -1368,7 +1616,7 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszSt
 
        if (ui32Len < ui32Space)
        {
-               
+               /* copy terminator */
                pui8Buffer[ui32WPtr] = (IMG_UINT8)pszString[ui32Len];
                ui32Len++;
                ui32WPtr++;
@@ -1377,7 +1625,7 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszSt
                        ui32WPtr = 0;
                }
 
-               
+               /* Write pointer, and length */
                psStream->ui32WPtr = ui32WPtr;
                psStream->ui32DataWritten+= ui32Len;
        } else
@@ -1395,6 +1643,16 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteString(PDBG_STREAM psStream,IMG_CHAR * pszSt
        return(ui32Len);
 }
 
+/*!****************************************************************************
+ @name         DBGDrivReadString
+ @brief                Reads string from debug stream
+ @param                psStream - stream
+ @param                pszString - string to read
+ @param                ui32Limit - max size to read
+ @return       -1; invalid stream
+                       0;      other error (e.g. stream not enabled)
+                       else number of characters read
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivReadString(PDBG_STREAM psStream,IMG_CHAR * pszString,IMG_UINT32 ui32Limit)
 {
        IMG_UINT32                              ui32OutLen;
@@ -1402,15 +1660,17 @@ IMG_UINT32 IMG_CALLCONV DBGDrivReadString(PDBG_STREAM psStream,IMG_CHAR * pszStr
        IMG_UINT32                              ui32Offset;
        IMG_UINT8                               *pui8Buff;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForRead(psStream))
        {
                return(0);
        }
 
-       
-
+       /*
+               Stream appears to be in list so carry on.
+       */
        pui8Buff = (IMG_UINT8 *)psStream->pvBase;
        ui32Offset = psStream->ui32RPtr;
 
@@ -1419,16 +1679,18 @@ IMG_UINT32 IMG_CALLCONV DBGDrivReadString(PDBG_STREAM psStream,IMG_CHAR * pszStr
                return(0);
        }
 
-       
-
+       /*
+               Find length of string.
+       */
        ui32Len = 0;
        while((pui8Buff[ui32Offset] != 0) && (ui32Offset != psStream->ui32WPtr))
        {
                ui32Offset++;
                ui32Len++;
 
-               
-
+               /*
+                       Reset offset if buffer wrapped.
+               */
                if (ui32Offset == psStream->ui32Size)
                {
                        ui32Offset = 0;
@@ -1437,15 +1699,17 @@ IMG_UINT32 IMG_CALLCONV DBGDrivReadString(PDBG_STREAM psStream,IMG_CHAR * pszStr
 
        ui32OutLen = ui32Len + 1;
 
-       
-
+       /*
+               Only copy string if target has enough space.
+       */
        if (ui32Len > ui32Limit)
        {
                return(0);
        }
 
-       
-
+       /*
+               Copy it.
+       */
        ui32Offset = psStream->ui32RPtr;
        ui32Len = 0;
 
@@ -1455,8 +1719,9 @@ IMG_UINT32 IMG_CALLCONV DBGDrivReadString(PDBG_STREAM psStream,IMG_CHAR * pszStr
                ui32Offset++;
                ui32Len++;
 
-               
-
+               /*
+                       If wrap as necessary
+               */
                if (ui32Offset == psStream->ui32Size)
                {
                        ui32Offset = 0;
@@ -1475,32 +1740,44 @@ IMG_UINT32 IMG_CALLCONV DBGDrivReadString(PDBG_STREAM psStream,IMG_CHAR * pszStr
        return(ui32OutLen);
 }
 
+/*!****************************************************************************
+ @name         DBGDrivWrite
+ @brief                Write binary buffer to stream (fixed size)
+ @param                psStream - stream
+ @param                pui8InBuf - buffer to write
+ @param                ui32InBuffSize - size
+ @param                ui32Level - verbosity level
+ @return       bytes written, 0 if recoverable error, -1 if unrecoverable error
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivWrite(PDBG_STREAM psMainStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level)
 {
        IMG_UINT32                              ui32Space;
        DBG_STREAM *psStream;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForWrite(psMainStream))
        {
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               Check debug level.
+       */
        if ((psMainStream->psCtrl->ui32DebugLevel & ui32Level) == 0)
        {
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               Only write data if debug mode adds up...
+       */
        if (psMainStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_FRAMED)
        {
                if      ((psMainStream->psCtrl->ui32Flags & DEBUG_FLAGS_ENABLESAMPLE) == 0)
                {
-                       
+                       /* throw away non-capturing data */
                        return(ui32InBuffSize);
                }
        }
@@ -1508,7 +1785,7 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWrite(PDBG_STREAM psMainStream,IMG_UINT8 * pui8In
        {
                if ((psMainStream->psCtrl->ui32Current != g_ui32HotKeyFrame) || (g_bHotKeyPressed == IMG_FALSE))
                {
-                       
+                       /* throw away non-capturing data */
                        return(ui32InBuffSize);
                }
        }
@@ -1522,8 +1799,9 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWrite(PDBG_STREAM psMainStream,IMG_UINT8 * pui8In
                psStream = psMainStream->psInitStream;
        }
 
-       
-
+       /*
+               How much space have we got in the buffer ?
+       */
        ui32Space=SpaceInStream(psStream);
 
        PVR_DPF((PVR_DBGDRIV_MESSAGE, "Recv %d b for %s: Roff = %x, WOff = %x",
@@ -1532,8 +1810,9 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWrite(PDBG_STREAM psMainStream,IMG_UINT8 * pui8In
                        psStream->ui32RPtr,
                        psStream->ui32WPtr));
 
-       
-
+       /*
+               Don't copy anything if we don't have space or buffers not enabled.
+       */
        if ((psStream->psCtrl->ui32OutMode & DEBUG_OUTMODE_STREAMENABLE) == 0)
        {
                PVR_DPF((PVR_DBG_ERROR, "DBGDrivWrite: buffer %x is disabled", (IMG_UINTPTR_T) psStream));
@@ -1546,15 +1825,17 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWrite(PDBG_STREAM psMainStream,IMG_UINT8 * pui8In
                return(0);
        }
 
-       
-
+       /*
+               Only copy what we can..
+       */
        if (ui32Space <= (ui32InBuffSize + 4))
        {
                ui32InBuffSize = ui32Space - 8;
        }
 
-       
-
+       /*
+               Write the stuff...
+       */
        Write(psStream,(IMG_UINT8 *) &ui32InBuffSize,4);
        Write(psStream,pui8InBuf,ui32InBuffSize);
 
@@ -1567,22 +1848,33 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWrite(PDBG_STREAM psMainStream,IMG_UINT8 * pui8In
        return(ui32InBuffSize);
 }
 
+/*!****************************************************************************
+ @name         DBGDrivWriteCM
+ @brief                Write capture mode data, wraps DBGDrivWrite
+ @param                psStream - stream
+ @param                pui8InBuf - input buffer
+ @param                ui32InBuffSize - buffer size
+ @param                ui32Level - verbosity level
+ @return       bytes written, 0 if recoverable error, -1 if unrecoverable error
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivWriteCM(PDBG_STREAM psStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForWrite(psStream))
        {
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               Only write data if debug mode adds up...
+       */
        if (psStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_FRAMED)
        {
                if      ((psStream->psCtrl->ui32Flags & DEBUG_FLAGS_ENABLESAMPLE) == 0)
                {
-                       
+                       /* throw away non-capturing data */
                        return(ui32InBuffSize);
                }
        }
@@ -1592,7 +1884,7 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteCM(PDBG_STREAM psStream,IMG_UINT8 * pui8InBu
                {
                        if ((psStream->psCtrl->ui32Current != g_ui32HotKeyFrame) || (g_bHotKeyPressed == IMG_FALSE))
                        {
-                               
+                               /* throw away non-capturing data */
                                return(ui32InBuffSize);
                        }
                }
@@ -1602,19 +1894,31 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteCM(PDBG_STREAM psStream,IMG_UINT8 * pui8InBu
 }
 
 
+/*!****************************************************************************
+ @name         DBGDrivWritePersist
+ @brief                Copies data from a buffer into selected stream's init phase. Stream size should be expandable.
+ @param                psStream - stream for output
+ @param                pui8InBuf - input buffer
+ @param                ui32InBuffSize - size of input
+ @param                ui32Level - not used
+ @return       bytes copied, 0 if recoverable error, -1 if unrecoverable error
+*****************************************************************************/
 static IMG_UINT32 DBGDrivWritePersist(PDBG_STREAM psMainStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level)
 {
        DBG_STREAM      *psStream;
        PVR_UNREFERENCED_PARAMETER(ui32Level);
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForWrite(psMainStream))
        {
                return(0xFFFFFFFFUL);
        }
 
-       
+       /* Always append persistent data to init phase so it's available on
+        * subsequent app runs.
+       */
        psStream = psMainStream->psInitStream;
        if(psStream->bCircularAllowed == IMG_TRUE)
        {
@@ -1631,20 +1935,31 @@ static IMG_UINT32 DBGDrivWritePersist(PDBG_STREAM psMainStream,IMG_UINT8 * pui8I
        return( WriteExpandingBuffer(psStream, pui8InBuf, ui32InBuffSize) );
 }
 
+/*!****************************************************************************
+ @name         DBGDrivWrite2
+ @brief                Copies data from a buffer into selected (expandable) stream.
+ @param                psMainStream - stream for output
+ @param                pui8InBuf - input buffer
+ @param                ui32InBuffSize - size of input
+ @param                ui32Level - debug level of input
+ @return       bytes copied, 0 if recoverable error, -1 if unrecoverable error
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivWrite2(PDBG_STREAM psMainStream,IMG_UINT8 * pui8InBuf,IMG_UINT32 ui32InBuffSize,IMG_UINT32 ui32Level)
 {
        DBG_STREAM      *psStream;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForWrite(psMainStream))
        {
                PVR_DPF((PVR_DBG_ERROR, "DBGDrivWrite2: stream not valid"));
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               Check debug level.
+       */
        if ((psMainStream->psCtrl->ui32DebugLevel & ui32Level) == 0)
        {
                return(0);
@@ -1668,13 +1983,23 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWrite2(PDBG_STREAM psMainStream,IMG_UINT8 * pui8I
        return( WriteExpandingBuffer(psStream, pui8InBuf, ui32InBuffSize) );
 }
 
+/*!****************************************************************************
+ @name         DBGDrivRead
+ @brief                Read from debug driver buffers
+ @param                psMainStream - stream
+ @param                bReadInitBuffer - whether to read from the init stream or the main stream
+ @param                ui32OutBuffSize - available space in client buffer
+ @param                pui8OutBuf - output buffer
+ @return       bytes read, 0 if failure occurred
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivRead(PDBG_STREAM psMainStream, IMG_BOOL bReadInitBuffer, IMG_UINT32 ui32OutBuffSize,IMG_UINT8 * pui8OutBuf)
 {
        IMG_UINT32 ui32Data;
        DBG_STREAM *psStream;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForRead(psMainStream))
        {
                PVR_DPF((PVR_DBG_ERROR, "DBGDrivRead: buffer %x is invalid", (IMG_UINTPTR_T) psMainStream));
@@ -1690,7 +2015,7 @@ IMG_UINT32 IMG_CALLCONV DBGDrivRead(PDBG_STREAM psMainStream, IMG_BOOL bReadInit
                psStream = psMainStream;
        }
 
-       
+       /* Don't read beyond the init phase marker point */
        if (psStream->ui32RPtr == psStream->ui32WPtr ||
                ((psStream->ui32InitPhaseWOff > 0) &&
                 (psStream->ui32RPtr >= psStream->ui32InitPhaseWOff)) )
@@ -1698,8 +2023,9 @@ IMG_UINT32 IMG_CALLCONV DBGDrivRead(PDBG_STREAM psMainStream, IMG_BOOL bReadInit
                return(0);
        }
 
-       
-
+       /*
+               Get amount of data in buffer.
+       */
        if (psStream->ui32RPtr <= psStream->ui32WPtr)
        {
                ui32Data = psStream->ui32WPtr - psStream->ui32RPtr;
@@ -1709,16 +2035,18 @@ IMG_UINT32 IMG_CALLCONV DBGDrivRead(PDBG_STREAM psMainStream, IMG_BOOL bReadInit
                ui32Data = psStream->ui32WPtr + (psStream->ui32Size - psStream->ui32RPtr);
        }
 
-       
-
+       /*
+               Don't read beyond the init phase marker point
+       */
        if ((psStream->ui32InitPhaseWOff > 0) &&
                (psStream->ui32InitPhaseWOff < psStream->ui32WPtr))
        {
                ui32Data = psStream->ui32InitPhaseWOff - psStream->ui32RPtr;
        }
 
-       
-
+       /*
+               Only transfer what target buffer can handle.
+       */
        if (ui32Data > ui32OutBuffSize)
        {
                ui32Data = ui32OutBuffSize;
@@ -1730,36 +2058,37 @@ IMG_UINT32 IMG_CALLCONV DBGDrivRead(PDBG_STREAM psMainStream, IMG_BOOL bReadInit
                        psStream->ui32RPtr,
                        psStream->ui32WPtr));
 
-       
-
+       /*
+               Split copy into two bits as necessay.
+       */
        if ((psStream->ui32RPtr + ui32Data) > psStream->ui32Size)
-       {       
+       {       /* Calc block 1 and block 2 sizes */
                IMG_UINT32 ui32B1 = psStream->ui32Size - psStream->ui32RPtr;
                IMG_UINT32 ui32B2 = ui32Data - ui32B1;
 
-               
+               /* Copy up to end of circular buffer */
                HostMemCopy((IMG_VOID *) pui8OutBuf,
                                (IMG_VOID *)((IMG_UINTPTR_T)psStream->pvBase + psStream->ui32RPtr),
                                ui32B1);
 
-               
+               /* Copy from start of circular buffer */
                HostMemCopy((IMG_VOID *)(pui8OutBuf + ui32B1),
                                psStream->pvBase,
                                ui32B2);
 
-               
+               /* Update read pointer now that we've copied the data out */
                psStream->ui32RPtr = ui32B2;
        }
        else
-       {       
+       {       /* Copy data from wherever */
                HostMemCopy((IMG_VOID *) pui8OutBuf,
                                (IMG_VOID *)((IMG_UINTPTR_T)psStream->pvBase + psStream->ui32RPtr),
                                ui32Data);
 
-               
+               /* Update read pointer now that we've copied the data out */
                psStream->ui32RPtr += ui32Data;
 
-               
+               /* Check for wrapping */
                if (psStream->ui32RPtr == psStream->ui32Size)
                {
                        psStream->ui32RPtr = 0;
@@ -1769,10 +2098,20 @@ IMG_UINT32 IMG_CALLCONV DBGDrivRead(PDBG_STREAM psMainStream, IMG_BOOL bReadInit
        return(ui32Data);
 }
 
+/*!****************************************************************************
+ @name         DBGDrivSetCaptureMode
+ @brief                Set capture mode
+ @param                psStream - stream
+ @param                ui32Mode - capturing mode
+ @param                ui32Start - start frame (frame mode only)
+ @param                ui32End - end frame (frame mode)
+ @param                ui32SampleRate - sampling frequency (frame mode)
+*****************************************************************************/
 void IMG_CALLCONV DBGDrivSetCaptureMode(PDBG_STREAM psStream,IMG_UINT32 ui32Mode,IMG_UINT32 ui32Start,IMG_UINT32 ui32End,IMG_UINT32 ui32SampleRate)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -1784,18 +2123,27 @@ void IMG_CALLCONV DBGDrivSetCaptureMode(PDBG_STREAM psStream,IMG_UINT32 ui32Mode
        psStream->psCtrl->ui32End = ui32End;
        psStream->psCtrl->ui32SampleRate = ui32SampleRate;
 
-       
-
+       /*
+               Activate hotkey it the stream is of this type.
+       */
        if (psStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_HOTKEY)
        {
                ActivateHotKeys(psStream);
        }
 }
 
+/*!****************************************************************************
+ @name         DBGDrivSetOutputMode
+ @brief                Change output mode
+ @param                psStream - stream
+ @param                ui32OutMode - output mode
+ @return       none
+*****************************************************************************/
 void IMG_CALLCONV DBGDrivSetOutputMode(PDBG_STREAM psStream,IMG_UINT32 ui32OutMode)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -1804,10 +2152,18 @@ void IMG_CALLCONV DBGDrivSetOutputMode(PDBG_STREAM psStream,IMG_UINT32 ui32OutMo
        psStream->psCtrl->ui32OutMode = ui32OutMode;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivSetDebugLevel
+ @brief                Change debug level
+ @param                psStream - stream
+ @param                ui32DebugLevel - verbosity level
+ @return       none
+*****************************************************************************/
 void IMG_CALLCONV DBGDrivSetDebugLevel(PDBG_STREAM psStream,IMG_UINT32 ui32DebugLevel)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -1816,10 +2172,18 @@ void IMG_CALLCONV DBGDrivSetDebugLevel(PDBG_STREAM psStream,IMG_UINT32 ui32Debug
        psStream->psCtrl->ui32DebugLevel = ui32DebugLevel;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivSetFrame
+ @brief                Advance frame counter
+ @param                psStream - stream
+ @param                ui32Frame - frame number
+ @return       none
+*****************************************************************************/
 void IMG_CALLCONV DBGDrivSetFrame(PDBG_STREAM psStream,IMG_UINT32 ui32Frame)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -1856,7 +2220,7 @@ void IMG_CALLCONV DBGDrivSetFrame(PDBG_STREAM psStream,IMG_UINT32 ui32Frame)
                }
        }
 
-       
+       /* Check to see if hotkey press has been registered (from keyboard filter) */
        if (g_bHotKeyRegistered)
        {
                g_bHotKeyRegistered = IMG_FALSE;
@@ -1865,23 +2229,26 @@ void IMG_CALLCONV DBGDrivSetFrame(PDBG_STREAM psStream,IMG_UINT32 ui32Frame)
 
                if (!g_bHotKeyPressed)
                {
-                       
-
+                       /*
+                               Capture the next frame.
+                       */
                        g_ui32HotKeyFrame = psStream->psCtrl->ui32Current + 2;
 
-                       
-
+                       /*
+                               Do the flag.
+                       */
                        g_bHotKeyPressed = IMG_TRUE;
                }
 
-               
-
+               /*
+                       If in framed hotkey mode, then set start frame.
+               */
                if (((psStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_FRAMED) != 0) && 
                        ((psStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_HOTKEY) != 0))
                {
                        if (!g_bHotkeyMiddump)
                        {
-                               
+                               /* Turn on */
                                g_ui32HotkeyMiddumpStart = g_ui32HotKeyFrame + 1;
                                g_ui32HotkeyMiddumpEnd = 0xffffffff;
                                g_bHotkeyMiddump = IMG_TRUE;
@@ -1889,7 +2256,7 @@ void IMG_CALLCONV DBGDrivSetFrame(PDBG_STREAM psStream,IMG_UINT32 ui32Frame)
                        }
                        else
                        {
-                               
+                               /* Turn off */
                                g_ui32HotkeyMiddumpEnd = g_ui32HotKeyFrame;
                                PVR_DPF((PVR_DBG_MESSAGE,"Turning off sampling\n"));
                        }
@@ -1897,18 +2264,26 @@ void IMG_CALLCONV DBGDrivSetFrame(PDBG_STREAM psStream,IMG_UINT32 ui32Frame)
 
        }
 
-       
-
+       /*
+               Clear the hotkey frame indicator when over that frame.
+       */
        if (psStream->psCtrl->ui32Current > g_ui32HotKeyFrame)
        {
                g_bHotKeyPressed = IMG_FALSE;
        }
 }
 
+/*!****************************************************************************
+ @name         DBGDrivGetFrame
+ @brief                Retrieve current frame number
+ @param                psStream - stream
+ @return       frame number
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivGetFrame(PDBG_STREAM psStream)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return(0);
@@ -1917,12 +2292,19 @@ IMG_UINT32 IMG_CALLCONV DBGDrivGetFrame(PDBG_STREAM psStream)
        return(psStream->psCtrl->ui32Current);
 }
 
+/*!****************************************************************************
+ @name         DBGDrivIsLastCaptureFrame
+ @brief                Is this the last frame to be captured?
+ @param                psStream - stream
+ @return       true if last capture frame, false otherwise
+*****************************************************************************/
 IMG_BOOL IMG_CALLCONV DBGDrivIsLastCaptureFrame(PDBG_STREAM psStream)
 {
        IMG_UINT32      ui32NextFrame;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return IMG_FALSE;
@@ -1939,12 +2321,20 @@ IMG_BOOL IMG_CALLCONV DBGDrivIsLastCaptureFrame(PDBG_STREAM psStream)
        return IMG_FALSE;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivIsCaptureFrame
+ @brief                Is this a capture frame?
+ @param                psStream - stream
+ @param                bCheckPreviousFrame - set if it needs to be 1 frame ahead
+ @return       true if capturing this frame, false otherwise
+*****************************************************************************/
 IMG_BOOL IMG_CALLCONV DBGDrivIsCaptureFrame(PDBG_STREAM psStream, IMG_BOOL bCheckPreviousFrame)
 {
        IMG_UINT32 ui32FrameShift = bCheckPreviousFrame ? 1UL : 0UL;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return IMG_FALSE;
@@ -1952,7 +2342,7 @@ IMG_BOOL IMG_CALLCONV DBGDrivIsCaptureFrame(PDBG_STREAM psStream, IMG_BOOL bChec
 
        if (psStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_FRAMED)
        {
-               
+               /* Needs to be one frame ahead, so disppatch can turn everything on */
                if (g_bHotkeyMiddump)
                {
                        if ((psStream->psCtrl->ui32Current >= (g_ui32HotkeyMiddumpStart - ui32FrameShift)) &&
@@ -1982,10 +2372,18 @@ IMG_BOOL IMG_CALLCONV DBGDrivIsCaptureFrame(PDBG_STREAM psStream, IMG_BOOL bChec
        return IMG_FALSE;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivOverrideMode
+ @brief                Override capture mode
+ @param                psStream - stream
+ @param                ui32Mode - capture mode
+ @return       none
+*****************************************************************************/
 void IMG_CALLCONV DBGDrivOverrideMode(PDBG_STREAM psStream,IMG_UINT32 ui32Mode)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -1994,10 +2392,16 @@ void IMG_CALLCONV DBGDrivOverrideMode(PDBG_STREAM psStream,IMG_UINT32 ui32Mode)
        psStream->psCtrl->ui32CapMode = ui32Mode;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivDefaultMode
+ @param                psStream - stream
+ @return       none
+*****************************************************************************/
 void IMG_CALLCONV DBGDrivDefaultMode(PDBG_STREAM psStream)
 {
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -2006,10 +2410,18 @@ void IMG_CALLCONV DBGDrivDefaultMode(PDBG_STREAM psStream)
        psStream->psCtrl->ui32CapMode = psStream->psCtrl->ui32DefaultMode;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivSetClientMarker
+ @brief        Sets the marker to prevent reading initphase beyond data on behalf of previous app
+ @param                psStream - stream
+ @param                ui32Marker - byte offset in init buffer
+ @return       nothing
+*****************************************************************************/
 IMG_VOID IMG_CALLCONV DBGDrivSetClientMarker(PDBG_STREAM psStream, IMG_UINT32 ui32Marker)
 {
-       
-
+       /*
+               Validate buffer
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -2018,10 +2430,17 @@ IMG_VOID IMG_CALLCONV DBGDrivSetClientMarker(PDBG_STREAM psStream, IMG_UINT32 ui
        psStream->ui32InitPhaseWOff = ui32Marker;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivSetMarker
+ @brief                Sets the marker in the stream to split output files
+ @param                psStream, ui32Marker
+ @return       nothing
+*****************************************************************************/
 void IMG_CALLCONV DBGDrivSetMarker(PDBG_STREAM psStream, IMG_UINT32 ui32Marker)
 {
-       
-
+       /*
+               Validate buffer
+       */
        if (!StreamValid(psStream))
        {
                return;
@@ -2030,10 +2449,17 @@ void IMG_CALLCONV DBGDrivSetMarker(PDBG_STREAM psStream, IMG_UINT32 ui32Marker)
        psStream->ui32Marker = ui32Marker;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivGetMarker
+ @brief        Gets the marker in the stream to split output files
+ @param                psStream - stream
+ @return       marker offset
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivGetMarker(PDBG_STREAM psStream)
 {
-       
-
+       /*
+               Validate buffer
+       */
        if (!StreamValid(psStream))
        {
                return 0;
@@ -2043,12 +2469,19 @@ IMG_UINT32 IMG_CALLCONV DBGDrivGetMarker(PDBG_STREAM psStream)
 }
 
 
+/*!****************************************************************************
+ @name         DBGDrivGetStreamOffset
+ @brief                Gets the amount of data written to the stream
+ @param                psMainStream - stream
+ @return       bytes written
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivGetStreamOffset(PDBG_STREAM psMainStream)
 {
        PDBG_STREAM psStream;
 
-       
-
+       /*
+               Validate buffer
+       */
        if (!StreamValid(psMainStream))
        {
                return 0;
@@ -2066,12 +2499,20 @@ IMG_UINT32 IMG_CALLCONV DBGDrivGetStreamOffset(PDBG_STREAM psMainStream)
        return psStream->ui32DataWritten;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivSetStreamOffset
+ @brief                Sets the amount of data written to the stream
+ @param                psMainStream - stream
+ @param                ui32StreamOffset - stream offset
+ @return       Nothing
+*****************************************************************************/
 IMG_VOID IMG_CALLCONV DBGDrivSetStreamOffset(PDBG_STREAM psMainStream, IMG_UINT32 ui32StreamOffset)
 {
        PDBG_STREAM psStream;
 
-       
-
+       /*
+               Validate buffer
+       */
        if (!StreamValid(psMainStream))
        {
                return;
@@ -2092,36 +2533,54 @@ IMG_VOID IMG_CALLCONV DBGDrivSetStreamOffset(PDBG_STREAM psMainStream, IMG_UINT3
        psStream->ui32DataWritten = ui32StreamOffset;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivGetServiceTable
+ @brief                get jump table for Services driver
+ @return       pointer to jump table
+*****************************************************************************/
 IMG_PVOID IMG_CALLCONV DBGDrivGetServiceTable(IMG_VOID)
 {
        return((IMG_PVOID)&g_sDBGKMServices);
 }
 
+/*!****************************************************************************
+ @name         DBGDrivWriteLF
+ @brief                Store data that should only be kept from the last frame dumped
+ @param                psStream - stream
+ @param                pui8InBuf - input buffer
+ @param                ui32InBuffSize - size
+ @param                ui32Level - verbosity level
+ @param                ui32Flags - flags
+ @return       bytes written
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivWriteLF(PDBG_STREAM psStream, IMG_UINT8 * pui8InBuf, IMG_UINT32 ui32InBuffSize, IMG_UINT32 ui32Level, IMG_UINT32 ui32Flags)
 {
        PDBG_LASTFRAME_BUFFER   psLFBuffer;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForWrite(psStream))
        {
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               Check debug level.
+       */
        if ((psStream->psCtrl->ui32DebugLevel & ui32Level) == 0)
        {
                return(0xFFFFFFFFUL);
        }
 
-       
-
+       /*
+               Only write data if debug mode adds up...
+       */
        if ((psStream->psCtrl->ui32CapMode & DEBUG_CAPMODE_FRAMED) != 0)
        {
                if      ((psStream->psCtrl->ui32Flags & DEBUG_FLAGS_ENABLESAMPLE) == 0)
                {
-                       
+                       /* throw away non-capturing data */
                        return(ui32InBuffSize);
                }
        }
@@ -2129,7 +2588,7 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteLF(PDBG_STREAM psStream, IMG_UINT8 * pui8InB
        {
                if ((psStream->psCtrl->ui32Current != g_ui32HotKeyFrame) || (g_bHotKeyPressed == IMG_FALSE))
                {
-                       
+                       /* throw away non-capturing data */
                        return(ui32InBuffSize);
                }
        }
@@ -2138,16 +2597,18 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteLF(PDBG_STREAM psStream, IMG_UINT8 * pui8InB
 
        if (ui32Flags & WRITELF_FLAGS_RESETBUF)
        {
-               
-
+               /*
+                       Copy the data into the buffer
+               */
                ui32InBuffSize = (ui32InBuffSize > LAST_FRAME_BUF_SIZE) ? LAST_FRAME_BUF_SIZE : ui32InBuffSize;
                HostMemCopy((IMG_VOID *)psLFBuffer->ui8Buffer, (IMG_VOID *)pui8InBuf, ui32InBuffSize);
                psLFBuffer->ui32BufLen = ui32InBuffSize;
        }
        else
        {
-               
-
+               /*
+                       Append the data to the end of the buffer
+               */
                ui32InBuffSize = ((psLFBuffer->ui32BufLen + ui32InBuffSize) > LAST_FRAME_BUF_SIZE) ? (LAST_FRAME_BUF_SIZE - psLFBuffer->ui32BufLen) : ui32InBuffSize;
                HostMemCopy((IMG_VOID *)(&psLFBuffer->ui8Buffer[psLFBuffer->ui32BufLen]), (IMG_VOID *)pui8InBuf, ui32InBuffSize);
                psLFBuffer->ui32BufLen += ui32InBuffSize;
@@ -2156,13 +2617,22 @@ IMG_UINT32 IMG_CALLCONV DBGDrivWriteLF(PDBG_STREAM psStream, IMG_UINT8 * pui8InB
        return(ui32InBuffSize);
 }
 
+/*!****************************************************************************
+ @name         DBGDrivReadLF
+ @brief                Read data that should only be kept from the last frame dumped
+ @param                psStream - stream
+ @param                ui32OutBuffSize - buffer size
+ @param                pui8OutBuf - output buffer
+ @return       bytes read
+*****************************************************************************/
 IMG_UINT32 IMG_CALLCONV DBGDrivReadLF(PDBG_STREAM psStream, IMG_UINT32 ui32OutBuffSize, IMG_UINT8 * pui8OutBuf)
 {
        PDBG_LASTFRAME_BUFFER   psLFBuffer;
        IMG_UINT32      ui32Data;
 
-       
-
+       /*
+               Validate buffer.
+       */
        if (!StreamValidForRead(psStream))
        {
                return(0);
@@ -2170,34 +2640,61 @@ IMG_UINT32 IMG_CALLCONV DBGDrivReadLF(PDBG_STREAM psStream, IMG_UINT32 ui32OutBu
 
        psLFBuffer = FindLFBuf(psStream);
 
-       
-
+       /*
+               Get amount of data to copy
+       */
        ui32Data = (ui32OutBuffSize < psLFBuffer->ui32BufLen) ? ui32OutBuffSize : psLFBuffer->ui32BufLen;
 
-       
-
+       /*
+               Copy the data into the buffer
+       */
        HostMemCopy((IMG_VOID *)pui8OutBuf, (IMG_VOID *)psLFBuffer->ui8Buffer, ui32Data);
 
        return ui32Data;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivStartInitPhase
+ @brief                Marks start of init phase
+ @param                psStream - stream
+ @return       void
+*****************************************************************************/
 IMG_VOID IMG_CALLCONV DBGDrivStartInitPhase(PDBG_STREAM psStream)
 {
        psStream->psCtrl->bInitPhaseComplete = IMG_FALSE;
 }
 
+/*!****************************************************************************
+ @name         DBGDrivStopInitPhase
+ @brief                Marks end of init phase
+ @param                psStream - stream
+ @return       void
+*****************************************************************************/
 IMG_VOID IMG_CALLCONV DBGDrivStopInitPhase(PDBG_STREAM psStream)
 {
        psStream->psCtrl->bInitPhaseComplete = IMG_TRUE;
 }
 
 #if defined(SUPPORT_DBGDRV_EVENT_OBJECTS)
+/*!****************************************************************************
+ @name         DBGDrivWaitForEvent
+ @brief                waits for an event
+ @param                eEvent - debug driver event
+ @return       void
+*****************************************************************************/
 IMG_VOID IMG_CALLCONV DBGDrivWaitForEvent(DBG_EVENT eEvent)
 {
        HostWaitForEvent(eEvent);
 }
 #endif
 
+/*!****************************************************************************
+ @name         ExpandStreamBuffer
+ @brief                allocates a new buffer when the current one is full
+ @param                psStream - stream
+ @param                ui32NewSize - new size
+ @return       IMG_TRUE - if allocation succeeded, IMG_FALSE - if not
+*****************************************************************************/
 IMG_BOOL ExpandStreamBuffer(PDBG_STREAM psStream, IMG_UINT32 ui32NewSize)
 {
        IMG_VOID *      pvNewBuf;
@@ -2206,19 +2703,22 @@ IMG_BOOL ExpandStreamBuffer(PDBG_STREAM psStream, IMG_UINT32 ui32NewSize)
        IMG_UINT32      ui32NewROffset;
        IMG_UINT32      ui32SpaceInOldBuf;
 
-       
-
+       /* 
+               First check new size is bigger than existing size 
+       */
        if (psStream->ui32Size >= ui32NewSize)
        {
                return IMG_FALSE;
        }
 
-       
-
+       /*
+               Calc space in old buffer 
+       */
        ui32SpaceInOldBuf = SpaceInStream(psStream);
 
-       
-
+       /*
+               Allocate new buffer 
+       */
        ui32NewSizeInPages = ((ui32NewSize + 0xfffUL) & ~0xfffUL) / 4096UL;
 
        if ((psStream->psCtrl->ui32Flags & DEBUG_FLAGS_USE_NONPAGED_MEM) != 0)
@@ -2237,13 +2737,15 @@ IMG_BOOL ExpandStreamBuffer(PDBG_STREAM psStream, IMG_UINT32 ui32NewSize)
 
        if(psStream->bCircularAllowed)
        {
-               
-
-
+               /*
+                       Copy over old buffer to new one, we place data at start of buffer
+                       even if Read offset is not at start of buffer
+               */
                if (psStream->ui32RPtr <= psStream->ui32WPtr)
                {
-                       
-
+                       /*
+                               No wrapping of data so copy data to start of new buffer 
+                       */
                HostMemCopy(pvNewBuf,
                                        (IMG_VOID *)((IMG_UINTPTR_T)psStream->pvBase + psStream->ui32RPtr),
                                        psStream->ui32WPtr - psStream->ui32RPtr);
@@ -2252,16 +2754,18 @@ IMG_BOOL ExpandStreamBuffer(PDBG_STREAM psStream, IMG_UINT32 ui32NewSize)
                {
                        IMG_UINT32      ui32FirstCopySize;
        
-                       
-
+                       /*
+                               The data has wrapped around the buffer, copy beginning of buffer first 
+                       */
                        ui32FirstCopySize = psStream->ui32Size - psStream->ui32RPtr;
        
                        HostMemCopy(pvNewBuf,
                                        (IMG_VOID *)((IMG_UINTPTR_T)psStream->pvBase + psStream->ui32RPtr),
                                        ui32FirstCopySize);
        
-                       
-
+                       /*
+                               Now second half 
+                       */
                        HostMemCopy((IMG_VOID *)((IMG_UINTPTR_T)pvNewBuf + ui32FirstCopySize),
                                        (IMG_VOID *)(IMG_PBYTE)psStream->pvBase,
                                        psStream->ui32WPtr);
@@ -2270,18 +2774,19 @@ IMG_BOOL ExpandStreamBuffer(PDBG_STREAM psStream, IMG_UINT32 ui32NewSize)
        }
        else
        {
-               
+               /* Copy everything in the old buffer to the new one */
                HostMemCopy(pvNewBuf, psStream->pvBase, psStream->ui32WPtr);
                ui32NewROffset = psStream->ui32RPtr;
        }
 
-       
-
-                                                        
+       /*
+               New Write offset is at end of data 
+       */                                                        
        ui32NewWOffset = psStream->ui32Size - ui32SpaceInOldBuf;
 
-       
-
+       /*
+               Free old buffer 
+       */
        if ((psStream->psCtrl->ui32Flags & DEBUG_FLAGS_USE_NONPAGED_MEM) != 0)
        {
                HostNonPageablePageFree(psStream->pvBase);
@@ -2291,8 +2796,9 @@ IMG_BOOL ExpandStreamBuffer(PDBG_STREAM psStream, IMG_UINT32 ui32NewSize)
                HostPageablePageFree(psStream->pvBase);
        }
 
-       
-
+       /*
+               Now set new params up 
+       */
        psStream->pvBase = pvNewBuf;
        psStream->ui32RPtr = ui32NewROffset;
        psStream->ui32WPtr = ui32NewWOffset;
@@ -2301,13 +2807,19 @@ IMG_BOOL ExpandStreamBuffer(PDBG_STREAM psStream, IMG_UINT32 ui32NewSize)
        return IMG_TRUE;
 }
 
+/*!****************************************************************************
+ @name         SpaceInStream
+ @brief                remaining space in stream
+ @param                psStream - stream
+ @return       bytes remaining
+*****************************************************************************/
 IMG_UINT32 SpaceInStream(PDBG_STREAM psStream)
 {
        IMG_UINT32      ui32Space;
 
        if (psStream->bCircularAllowed)
        {
-               
+               /* Allow overwriting the buffer which was already read */
        if (psStream->ui32RPtr > psStream->ui32WPtr)
        {
                ui32Space = psStream->ui32RPtr - psStream->ui32WPtr;
@@ -2319,7 +2831,7 @@ IMG_UINT32 SpaceInStream(PDBG_STREAM psStream)
        }
        else
        {
-               
+               /* Don't overwrite anything */
                ui32Space = psStream->ui32Size - psStream->ui32WPtr;
        }
 
@@ -2327,6 +2839,11 @@ IMG_UINT32 SpaceInStream(PDBG_STREAM psStream)
 }
 
 
+/*!****************************************************************************
+ @name         DestroyAllStreams
+ @brief                delete all streams in list
+ @return       none
+*****************************************************************************/
 void DestroyAllStreams(void)
 {
        while (g_psStreamList != IMG_NULL)
@@ -2336,6 +2853,12 @@ void DestroyAllStreams(void)
        return;
 }
 
+/*!****************************************************************************
+ @name         FindLFBuf
+ @brief                finds last frame stream
+ @param                psStream - stream to find
+ @return       stream if found, NULL otherwise
+*****************************************************************************/
 PDBG_LASTFRAME_BUFFER FindLFBuf(PDBG_STREAM psStream)
 {
        PDBG_LASTFRAME_BUFFER   psLFBuffer;
@@ -2355,3 +2878,6 @@ PDBG_LASTFRAME_BUFFER FindLFBuf(PDBG_STREAM psStream)
        return psLFBuffer;
 }
 
+/******************************************************************************
+ End of file (DBGDRIV.C)
+******************************************************************************/
index 2db4843..d58c62d 100644 (file)
@@ -1,32 +1,50 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Debug Driver interface definition.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _DBGDRIV_
 #define _DBGDRIV_
 
+/*****************************************************************************
+ The odd constant or two
+*****************************************************************************/
 #define BUFFER_SIZE 64*PAGESIZE
 
 #define DBGDRIV_VERSION        0x100
@@ -38,6 +56,9 @@
 
 extern IMG_VOID *      g_pvAPIMutex;
 
+/*****************************************************************************
+ KM mode functions
+*****************************************************************************/
 IMG_VOID * IMG_CALLCONV DBGDrivCreateStream(IMG_CHAR *         pszName,
                                                                   IMG_UINT32   ui32CapMode,
                                                                   IMG_UINT32   ui32OutMode,
@@ -75,17 +96,26 @@ IMG_VOID   IMG_CALLCONV DBGDrivWaitForEvent(DBG_EVENT eEvent);
 
 IMG_VOID DestroyAllStreams(IMG_VOID);
 
+/*****************************************************************************
+ Function prototypes
+*****************************************************************************/
 IMG_UINT32 AtoI(IMG_CHAR *szIn);
 
 IMG_VOID HostMemSet(IMG_VOID *pvDest,IMG_UINT8 ui8Value,IMG_UINT32 ui32Size);
 IMG_VOID HostMemCopy(IMG_VOID *pvDest,IMG_VOID *pvSrc,IMG_UINT32 ui32Size);
 IMG_VOID MonoOut(IMG_CHAR * pszString,IMG_BOOL bNewLine);
 
+/*****************************************************************************
+ Secure handle Function prototypes
+*****************************************************************************/
 IMG_SID PStream2SID(PDBG_STREAM psStream);
 PDBG_STREAM SID2PStream(IMG_SID hStream); 
 IMG_BOOL AddSIDEntry(PDBG_STREAM psStream);
 IMG_BOOL RemoveSIDEntry(PDBG_STREAM psStream);
 
+/*****************************************************************************
+ Declarations for Service table entry points
+*****************************************************************************/
 IMG_VOID * IMG_CALLCONV ExtDBGDrivCreateStream(IMG_CHAR *      pszName, IMG_UINT32 ui32CapMode, IMG_UINT32     ui32OutMode, IMG_UINT32 ui32Flags, IMG_UINT32 ui32Size);
 IMG_VOID   IMG_CALLCONV ExtDBGDrivDestroyStream(PDBG_STREAM psStream);
 IMG_VOID * IMG_CALLCONV ExtDBGDrivFindStream(IMG_CHAR * pszName, IMG_BOOL bResetStream);
@@ -120,3 +150,6 @@ IMG_UINT32 IMG_CALLCONV ExtDBGDrivWritePersist(PDBG_STREAM psStream,IMG_UINT8 *p
 
 #endif
 
+/*****************************************************************************
+ End of file (DBGDRIV.H)
+*****************************************************************************/
index 130c146..0909e6d 100644 (file)
@@ -1,35 +1,57 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          IOCTL implementations for debug device.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _IOCTL_
 #define _IOCTL_
 
+/*****************************************************************************
+ Global vars
+*****************************************************************************/
+
 #define MAX_DBGVXD_W32_API 25
 
 extern IMG_UINT32 (*g_DBGDrivProc[MAX_DBGVXD_W32_API])(IMG_VOID *, IMG_VOID *);
 
 #endif
 
+/*****************************************************************************
+ End of file (IOCTL.H)
+*****************************************************************************/
index ddffb3f..a9d37a6 100644 (file)
@@ -1,33 +1,50 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Resource Handle Manager
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Provide resource handle management
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #include "img_defs.h"
 #include "dbgdrvif.h"
 #include "dbgdriv.h"
 
+/* max number of streams held in SID info table */
 #define MAX_SID_ENTRIES                8
 
 typedef struct _SID_INFO
@@ -47,7 +64,7 @@ IMG_SID PStream2SID(PDBG_STREAM psStream)
                {
                        if (psStream == gaSID_Xlat_Table[iIdx].psStream)
                        {
-                               
+                               /* idx is one based */
                                return (IMG_SID)iIdx+1;
                        }
                }
@@ -59,7 +76,7 @@ IMG_SID PStream2SID(PDBG_STREAM psStream)
 
 PDBG_STREAM SID2PStream(IMG_SID hStream)
 {
-       
+       /* changed to zero based */
        IMG_INT32 iIdx = (IMG_INT32)hStream-1;
 
        if (iIdx >= 0 && iIdx < MAX_SID_ENTRIES)
@@ -83,13 +100,13 @@ IMG_BOOL AddSIDEntry(PDBG_STREAM psStream)
                {
                        if (psStream == gaSID_Xlat_Table[iIdx].psStream)
                        {
-                               
+                               /* already created */
                                return IMG_TRUE;
                        }
 
                        if (gaSID_Xlat_Table[iIdx].psStream == (PDBG_STREAM)IMG_NULL)
                        {
-                               
+                               /* free entry */
                                gaSID_Xlat_Table[iIdx].psStream = psStream;
                                return IMG_TRUE;
                        }
@@ -119,3 +136,6 @@ IMG_BOOL RemoveSIDEntry(PDBG_STREAM psStream)
 }
 
 
+/******************************************************************************
+ End of file (handle.c)
+******************************************************************************/
index 70192fb..e92ad9a 100644 (file)
@@ -1,35 +1,56 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Host function definitions for debug device.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _HOSTFUNC_
 #define _HOSTFUNC_
 
+/*****************************************************************************
+ Defines
+*****************************************************************************/
 #define HOST_PAGESIZE                  (4096)
 #define DBG_MEMORY_INITIALIZER (0xe2)
 
+/*****************************************************************************
+ Function prototypes
+*****************************************************************************/
 IMG_UINT32 HostReadRegistryDWORDFromString(IMG_CHAR *pcKey, IMG_CHAR *pcValueName, IMG_UINT32 *pui32Data);
 
 IMG_VOID * HostPageablePageAlloc(IMG_UINT32 ui32Pages);
@@ -52,7 +73,10 @@ IMG_INT32 HostCreateEventObjects(IMG_VOID);
 IMG_VOID HostWaitForEvent(DBG_EVENT eEvent);
 IMG_VOID HostSignalEvent(DBG_EVENT eEvent);
 IMG_VOID HostDestroyEventObjects(IMG_VOID);
-#endif 
+#endif /*defined(SUPPORT_DBGDRV_EVENT_OBJECTS) */
 
 #endif
 
+/*****************************************************************************
+ End of file (HOSTFUNC.H)
+*****************************************************************************/
index 62c89e3..6bf20a6 100644 (file)
@@ -1,31 +1,47 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
-
-#if (!defined(LINUX) && !defined(__QNXNTO__))
+/*************************************************************************/ /*!
+@Title          Debug driver utilities implementations.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Hotkey stuff
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
+
+
+#if !defined(LINUX) && !defined(__QNXNTO__)
 #include <ntddk.h>
 #include <windef.h>
 #endif
 
 
 
+/*****************************************************************************
+ Global vars
+*****************************************************************************/
 
 IMG_UINT32     g_ui32HotKeyFrame = 0xFFFFFFFF;
 IMG_BOOL       g_bHotKeyPressed = IMG_FALSE;
 IMG_BOOL       g_bHotKeyRegistered = IMG_FALSE;
 
+/* Hotkey stuff */
 PRIVATEHOTKEYDATA    g_PrivateHotKeyData;
 
 
+/*****************************************************************************
+ Code
+*****************************************************************************/
+
+
+/******************************************************************************
+ * Function Name: ReadInHotKeys
+ *
+ * Inputs       : none
+ * Outputs      : -
+ * Returns      : nothing
+ * Globals Used : -
+ *
+ * Description  : Gets Hot key entries from system.ini
+ *****************************************************************************/
 IMG_VOID ReadInHotKeys(IMG_VOID)
 {
-       g_PrivateHotKeyData.ui32ScanCode = 0x58;        
+       g_PrivateHotKeyData.ui32ScanCode = 0x58;        /* F12  */
        g_PrivateHotKeyData.ui32ShiftState = 0x0;
 
-       
-
-#if 0
-       if (_RegOpenKey(HKEY_LOCAL_MACHINE,pszRegPath,&hKey) == ERROR_SUCCESS)
-       {
-               
-
-               QueryReg(hKey,"ui32ScanCode",&g_PrivateHotKeyData.ui32ScanCode);
-               QueryReg(hKey,"ui32ShiftState",&g_PrivateHotKeyData.ui32ShiftState);
-       }
-#else
+       /*
+               Find buffer names etc..
+       */
        HostReadRegistryDWORDFromString("DEBUG\\Streams", "ui32ScanCode"  , &g_PrivateHotKeyData.ui32ScanCode);
        HostReadRegistryDWORDFromString("DEBUG\\Streams", "ui32ShiftState", &g_PrivateHotKeyData.ui32ShiftState);
-#endif
 }
 
+/******************************************************************************
+ * Function Name: RegisterKeyPressed
+ *
+ * Inputs       : IMG_UINT32 dwui32ScanCode, PHOTKEYINFO pInfo
+ * Outputs      : -
+ * Returns      : nothing
+ * Globals Used : -
+ *
+ * Description  : Called when hotkey pressed.
+ *****************************************************************************/
 IMG_VOID RegisterKeyPressed(IMG_UINT32 dwui32ScanCode, PHOTKEYINFO pInfo)
 {
        PDBG_STREAM     psStream;
@@ -83,33 +119,48 @@ IMG_VOID RegisterKeyPressed(IMG_UINT32 dwui32ScanCode, PHOTKEYINFO pInfo)
 
                if (!g_bHotKeyPressed)
                {
-                       
-
+                       /*
+                               Capture the next frame.
+                       */
                        g_ui32HotKeyFrame = psStream->psCtrl->ui32Current + 2;
 
-                       
-
+                       /*
+                               Do the flag.
+                       */
                        g_bHotKeyPressed = IMG_TRUE;
                }
        }
 }
 
+/******************************************************************************
+ * Function Name: ActivateHotKeys
+ *
+ * Inputs       : -
+ * Outputs      : -
+ * Returns      : -
+ * Globals Used : -
+ *
+ * Description  : Installs HotKey callbacks
+ *****************************************************************************/
 IMG_VOID ActivateHotKeys(PDBG_STREAM psStream)
 {
-       
-
+       /*
+               Setup hotkeys.
+       */
        ReadInHotKeys();
 
-       
-
+       /*
+               Has it already been allocated.
+       */
        if (!g_PrivateHotKeyData.sHotKeyInfo.hHotKey)
        {
                if (g_PrivateHotKeyData.ui32ScanCode != 0)
                {
                        PVR_DPF((PVR_DBG_MESSAGE,"Activate HotKey for PDUMP.\n"));
 
-                       
-
+                       /*
+                               Add in stream data.
+                       */
                        g_PrivateHotKeyData.sHotKeyInfo.pvStream = psStream;
 
                        DefineHotKey(g_PrivateHotKeyData.ui32ScanCode, g_PrivateHotKeyData.ui32ShiftState, &g_PrivateHotKeyData.sHotKeyInfo);
@@ -121,6 +172,16 @@ IMG_VOID ActivateHotKeys(PDBG_STREAM psStream)
        }
 }
 
+/******************************************************************************
+ * Function Name: DeactivateHotKeys
+ *
+ * Inputs       : -
+ * Outputs      : -
+ * Returns      : -
+ * Globals Used : -
+ *
+ * Description  : Removes HotKey callbacks
+ *****************************************************************************/
 IMG_VOID DeactivateHotKeys(IMG_VOID)
 {
        if (g_PrivateHotKeyData.sHotKeyInfo.hHotKey != 0)
@@ -133,3 +194,6 @@ IMG_VOID DeactivateHotKeys(IMG_VOID)
 }
 
 
+/*****************************************************************************
+ End of file (HOTKEY.C)
+*****************************************************************************/
index c5d84bb..7aa2952 100644 (file)
@@ -1,28 +1,44 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
+/*************************************************************************/ /*!
+@Title          Debug driver utilities header file.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@Description    Hotkey stuff
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 #ifndef _HOTKEY_
 #define _HOTKEY_
@@ -37,7 +53,7 @@ typedef struct _hotkeyinfo
        IMG_UINT32 ui32ShiftState;
        IMG_UINT32 ui32HotKeyProc;
        IMG_VOID *pvStream;
-       IMG_UINT32 hHotKey;                     
+       IMG_UINT32 hHotKey;                     /* handle.      */
 } HOTKEYINFO, *PHOTKEYINFO;
 
 typedef struct _privatehotkeydata
@@ -48,6 +64,9 @@ typedef struct _privatehotkeydata
 } PRIVATEHOTKEYDATA, *PPRIVATEHOTKEYDATA;
 
 
+/*****************************************************************************
+ Hotkey stuff
+*****************************************************************************/
 IMG_VOID ReadInHotKeys (IMG_VOID);
 IMG_VOID ActivateHotKeys(PDBG_STREAM psStream);
 IMG_VOID DeactivateHotKeys(IMG_VOID);
@@ -58,3 +77,6 @@ IMG_VOID RegisterKeyPressed (IMG_UINT32 ui32ScanCode, PHOTKEYINFO psInfo);
 
 #endif
 
+/*****************************************************************************
+ End of file (HOTKEY.H)
+*****************************************************************************/
index 47487b0..1767a9b 100644 (file)
@@ -1,35 +1,49 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          IOCTL implementations for debug device.
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 
 
 #ifdef LINUX
 #include <asm/uaccess.h>
 #include "pvr_uaccess.h"
-#endif 
+#endif /* LINUX */
 
 #include "img_types.h"
 #include "dbgdrvif.h"
 #include "dbgdriv_ioctl.h"
 
 
+/*****************************************************************************
+ Code
+*****************************************************************************/
+
+/*****************************************************************************
+ FUNCTION      :       DBGDrivCreateStream
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivCreateStream(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_CREATESTREAM psIn;
@@ -66,6 +93,15 @@ static IMG_UINT32 DBGDIOCDrivCreateStream(IMG_VOID * pvInBuffer, IMG_VOID * pvOu
        return(IMG_TRUE);
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivDestroyStream
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivDestroyStream(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_STREAM *ppsStream;
@@ -81,6 +117,15 @@ static IMG_UINT32 DBGDIOCDrivDestroyStream(IMG_VOID * pvInBuffer, IMG_VOID * pvO
        return(IMG_TRUE);
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivGetStream
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivGetStream(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_FINDSTREAM psParams;
@@ -94,6 +139,15 @@ static IMG_UINT32 DBGDIOCDrivGetStream(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBu
        return(IMG_TRUE);
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivWriteString
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivWriteString(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_WRITESTRING psParams;
@@ -111,12 +165,21 @@ static IMG_UINT32 DBGDIOCDrivWriteString(IMG_VOID * pvInBuffer, IMG_VOID * pvOut
        }
        else
        {
-               
+               /* invalid SID */
                *pui32OutLen = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivWriteStringCM
+
+ PURPOSE       :       Same as DBGDrivWriteString, but takes notice of capture mode.
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivWriteStringCM(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_WRITESTRING psParams;
@@ -134,12 +197,21 @@ static IMG_UINT32 DBGDIOCDrivWriteStringCM(IMG_VOID * pvInBuffer, IMG_VOID * pvO
        }
        else
        {
-               
+               /* invalid SID */
                *pui32OutLen = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivReadString
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivReadString(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        IMG_UINT32 * pui32OutLen;
@@ -158,12 +230,21 @@ static IMG_UINT32 DBGDIOCDrivReadString(IMG_VOID * pvInBuffer, IMG_VOID * pvOutB
        }
        else
        {
-               
+               /* invalid SID */
                *pui32OutLen = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivWrite
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivWrite(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        IMG_UINT32 *    pui32BytesCopied;
@@ -184,12 +265,21 @@ static IMG_UINT32 DBGDIOCDrivWrite(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer
        }
        else
        {
-               
+               /* invalid SID */
                *pui32BytesCopied = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivWrite2
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivWrite2(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        IMG_UINT32 *    pui32BytesCopied;
@@ -210,12 +300,21 @@ static IMG_UINT32 DBGDIOCDrivWrite2(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffe
        }
        else
        {
-               
+               /* invalid SID */
                *pui32BytesCopied = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivWriteCM
+
+ PURPOSE       :       Same as DBGDIOCDrivWrite2, but takes notice of capture mode.
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivWriteCM(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        IMG_UINT32 *    pui32BytesCopied;
@@ -236,12 +335,21 @@ static IMG_UINT32 DBGDIOCDrivWriteCM(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuff
        }
        else
        {
-               
+               /* invalid SID */
                *pui32BytesCopied = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivRead
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivRead(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        IMG_UINT32 *    pui32BytesCopied;
@@ -262,12 +370,21 @@ static IMG_UINT32 DBGDIOCDrivRead(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
        }
        else
        {
-               
+               /* invalid SID */
                *pui32BytesCopied = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDIOCDrivSetCaptureMode
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivSetCaptureMode(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_SETDEBUGMODE    psParams;
@@ -288,11 +405,20 @@ static IMG_UINT32 DBGDIOCDrivSetCaptureMode(IMG_VOID * pvInBuffer, IMG_VOID * pv
        }
        else
        {
-               
+               /* invalid SID */
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDIOCDrivSetOutMode
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivSetOutMode(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_SETDEBUGOUTMODE psParams;
@@ -309,11 +435,20 @@ static IMG_UINT32 DBGDIOCDrivSetOutMode(IMG_VOID * pvInBuffer, IMG_VOID * pvOutB
        }
        else
        {
-               
+               /* invalid SID */
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDIOCDrivSetDebugLevel
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivSetDebugLevel(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_SETDEBUGLEVEL psParams;
@@ -330,11 +465,20 @@ static IMG_UINT32 DBGDIOCDrivSetDebugLevel(IMG_VOID * pvInBuffer, IMG_VOID * pvO
        }
        else
        {
-               
+               /* invalid SID */
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivSetFrame
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivSetFrame(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_SETFRAME        psParams;
@@ -351,11 +495,20 @@ static IMG_UINT32 DBGDIOCDrivSetFrame(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuf
        }
        else
        {
-               
+               /* invalid SID */
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivGetFrame
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivGetFrame(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_STREAM  psStream;
@@ -371,12 +524,21 @@ static IMG_UINT32 DBGDIOCDrivGetFrame(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuf
        }
        else
        {
-               
+               /* invalid SID */
                *pui32Current = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDIOCDrivIsCaptureFrame
+
+ PURPOSE       :       Determines if this frame is a capture frame
+
+ PARAMETERS    :
+
+ RETURNS       :       IMG_TRUE if current frame is to be captured
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivIsCaptureFrame(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_ISCAPTUREFRAME psParams;
@@ -395,12 +557,21 @@ static IMG_UINT32 DBGDIOCDrivIsCaptureFrame(IMG_VOID * pvInBuffer, IMG_VOID * pv
        }
        else
        {
-               
+               /* invalid SID */
                *pui32Current = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivOverrideMode
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivOverrideMode(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_OVERRIDEMODE    psParams;
@@ -417,11 +588,20 @@ static IMG_UINT32 DBGDIOCDrivOverrideMode(IMG_VOID * pvInBuffer, IMG_VOID * pvOu
        }
        else
        {
-               
+               /* invalid SID */
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivDefaultMode
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivDefaultMode(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_STREAM  psStream;
@@ -436,11 +616,20 @@ static IMG_UINT32 DBGDIOCDrivDefaultMode(IMG_VOID * pvInBuffer, IMG_VOID * pvOut
        }
        else
        {
-               
+               /* invalid SID */
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      : DBGDIOCDrivSetMarker
+
+ PURPOSE       : Sets the marker in the stream to split output files
+
+ PARAMETERS    : pvInBuffer, pvOutBuffer
+
+ RETURNS       : success
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivSetMarker(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_SETMARKER       psParams;
@@ -457,11 +646,20 @@ static IMG_UINT32 DBGDIOCDrivSetMarker(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBu
        }
        else
        {
-               
+               /* invalid SID */
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      : DBGDIOCDrivGetMarker
+
+ PURPOSE       : Gets the marker in the stream to split output files
+
+ PARAMETERS    : pvInBuffer, pvOutBuffer
+
+ RETURNS       : success
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivGetMarker(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_STREAM  psStream;
@@ -477,12 +675,21 @@ static IMG_UINT32 DBGDIOCDrivGetMarker(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBu
        }
        else
        {
-               
+               /* invalid SID */
                *pui32Current = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDrivGetServiceTable
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivGetServiceTable(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        IMG_PVOID *     ppvOut;
@@ -495,6 +702,15 @@ static IMG_UINT32 DBGDIOCDrivGetServiceTable(IMG_VOID * pvInBuffer, IMG_VOID * p
     return(IMG_TRUE);
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDIOCDrivWriteLF
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivWriteLF(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        PDBG_IN_WRITE_LF psInParams;
@@ -516,11 +732,20 @@ static IMG_UINT32 DBGDIOCDrivWriteLF(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuff
        }
        else
        {
-               
+               /* invalid SID */
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDIOCDrivReadLF
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivReadLF(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        IMG_UINT32 *    pui32BytesCopied;
@@ -540,12 +765,21 @@ static IMG_UINT32 DBGDIOCDrivReadLF(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffe
        }
        else
        {
-               
+               /* invalid SID */
                *pui32BytesCopied = 0;
                return(IMG_FALSE);
        }
 }
 
+/*****************************************************************************
+ FUNCTION      :       DBGDIOCDrivWaitForEvent
+
+ PURPOSE       :
+
+ PARAMETERS    :
+
+ RETURNS       :
+*****************************************************************************/
 static IMG_UINT32 DBGDIOCDrivWaitForEvent(IMG_VOID * pvInBuffer, IMG_VOID * pvOutBuffer)
 {
        DBG_EVENT eEvent = (DBG_EVENT)(*(IMG_UINT32 *)pvInBuffer);
@@ -557,6 +791,9 @@ static IMG_UINT32 DBGDIOCDrivWaitForEvent(IMG_VOID * pvInBuffer, IMG_VOID * pvOu
        return(IMG_TRUE);
 }
 
+/*
+       VxD DIOC interface jump table.
+*/
 IMG_UINT32 (*g_DBGDrivProc[25])(IMG_VOID *, IMG_VOID *) =
 {
        DBGDIOCDrivCreateStream,
@@ -585,3 +822,6 @@ IMG_UINT32 (*g_DBGDrivProc[25])(IMG_VOID *, IMG_VOID *) =
        DBGDIOCDrivWaitForEvent
 };
 
+/*****************************************************************************
+ End of file (IOCTL.C)
+*****************************************************************************/
index 18c8898..5d5e9ef 100644 (file)
@@ -1,29 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Debug driver file
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #include <linux/version.h>
 #include <linux/errno.h>
 #include <linux/module.h>
@@ -46,7 +60,7 @@
 #include <linux/wait.h>
 #include <linux/jiffies.h>
 #include <linux/delay.h>
-#endif 
+#endif /* defined(SUPPORT_DBGDRV_EVENT_OBJECTS) */
 
 #include "img_types.h"
 #include "pvr_debug.h"
@@ -61,6 +75,24 @@ IMG_UINT32   gPVRDebugLevel = (DBGPRIV_FATAL | DBGPRIV_ERROR | DBGPRIV_WARNING);
 #define PVR_STRING_TERMINATOR          '\0'
 #define PVR_IS_FILE_SEPARATOR(character) ( ((character) == '\\') || ((character) == '/') )
 
+/******************************************************************************/
+
+
+/*!
+******************************************************************************
+
+ @Function     PVRSRVDebugPrintf
+       
+ @Description  To output a debug message to the user
+
+ @Input uDebugLevel: The current debug level
+ @Input pszFile:     The source file generating the message
+ @Input uLine:       The line of the source file
+ @Input pszFormat:   The message format string
+ @Input ...:         Zero or more arguments for use by the format string
+
+ @Return none
+******************************************************************************/
 void PVRSRVDebugPrintf (
                                                IMG_UINT32      ui32DebugLevel,
                                                const IMG_CHAR* pszFileName,
@@ -79,7 +111,7 @@ void PVRSRVDebugPrintf       (
        {
                pszFileName = pszLeafName;
        }
-#endif 
+#endif /* __sh__ */
 
        bTrace = (IMG_BOOL)(ui32DebugLevel & DBGPRIV_CALLTRACE) ? IMG_TRUE : IMG_FALSE;
 
@@ -90,13 +122,14 @@ void PVRSRVDebugPrintf     (
                char *szBufferEnd = szBuffer;
                char *szBufferLimit = szBuffer + sizeof(szBuffer) - 1;
 
-               
+               /* The Limit - End pointer arithmetic we're doing in snprintf
+                  ensures that our buffer remains null terminated from this */
                *szBufferLimit = '\0';
 
                snprintf(szBufferEnd, szBufferLimit - szBufferEnd, "PVR_K:");
                szBufferEnd += strlen(szBufferEnd);
 
-               
+               /* Add in the level of warning */
                if (bTrace == IMG_FALSE)
                {
                        switch(ui32DebugLevel)
@@ -142,7 +175,9 @@ void PVRSRVDebugPrintf      (
                va_end (vaArgs);
                szBufferEnd += strlen(szBufferEnd);
 
-               
+               /*
+                * Metrics and Traces don't need a location
+                */
                if (bTrace == IMG_FALSE)
                {
                        snprintf(szBufferEnd, szBufferLimit - szBufferEnd, 
@@ -153,13 +188,43 @@ void PVRSRVDebugPrintf    (
                printk(KERN_INFO "%s\r\n", szBuffer);
        }
 }
-#endif 
+#endif /* defined(DEBUG) && !defined(SUPPORT_DRI_DRM) */
+
+/*!
+******************************************************************************
+
+ @Function     HostMemSet
+
+ @Description Function that does the same as the C memset() function
 
+ @Modified *pvDest :   pointer to start of buffer to be set
+
+ @Input    ui8Value:   value to set each byte to
+
+ @Input    ui32Size :  number of bytes to set
+
+ @Return   IMG_VOID
+
+******************************************************************************/
 IMG_VOID HostMemSet(IMG_VOID *pvDest, IMG_UINT8 ui8Value, IMG_UINT32 ui32Size)
 {
        memset(pvDest, (int) ui8Value, (size_t) ui32Size);
 }
 
+/*!
+******************************************************************************
+
+ @Function             HostMemCopy
+
+ @Description  Function that does the same as the C memscpy() function
+
+ @Input    pvDst - pointer to dst
+ @Output   pvSrc - pointer to src
+ @Input    ui32Size - bytes to copy
+
+ @Return  none
+
+******************************************************************************/
 IMG_VOID HostMemCopy(IMG_VOID *pvDst, IMG_VOID *pvSrc, IMG_UINT32 ui32Size)
 {
 #if defined(USE_UNOPTIMISED_MEMCPY)
@@ -179,13 +244,13 @@ IMG_VOID HostMemCopy(IMG_VOID *pvDst, IMG_VOID *pvSrc, IMG_UINT32 ui32Size)
 
 IMG_UINT32 HostReadRegistryDWORDFromString(char *pcKey, char *pcValueName, IMG_UINT32 *pui32Data)
 {
-    
+    /* FIXME: Not yet implemented */
        return 0;
 }
 
 IMG_VOID * HostPageablePageAlloc(IMG_UINT32 ui32Pages)
 {
-    return (void*)vmalloc(ui32Pages * PAGE_SIZE);
+    return (void*)vmalloc(ui32Pages * PAGE_SIZE);/*, GFP_KERNEL);*/
 }
 
 IMG_VOID HostPageablePageFree(IMG_VOID * pvBase)
@@ -195,7 +260,7 @@ IMG_VOID HostPageablePageFree(IMG_VOID * pvBase)
 
 IMG_VOID * HostNonPageablePageAlloc(IMG_UINT32 ui32Pages)
 {
-    return (void*)vmalloc(ui32Pages * PAGE_SIZE);
+    return (void*)vmalloc(ui32Pages * PAGE_SIZE);/*, GFP_KERNEL);*/
 }
 
 IMG_VOID HostNonPageablePageFree(IMG_VOID * pvBase)
@@ -205,18 +270,18 @@ IMG_VOID HostNonPageablePageFree(IMG_VOID * pvBase)
 
 IMG_VOID * HostMapKrnBufIntoUser(IMG_VOID * pvKrnAddr, IMG_UINT32 ui32Size, IMG_VOID **ppvMdl)
 {
-    
+    /* FIXME: Not yet implemented */
        return IMG_NULL;
 }
 
 IMG_VOID HostUnMapKrnBufFromUser(IMG_VOID * pvUserAddr, IMG_VOID * pvMdl, IMG_VOID * pvProcess)
 {
-    
+    /* FIXME: Not yet implemented */
 }
 
 IMG_VOID HostCreateRegDeclStreams(IMG_VOID)
 {
-    
+    /* FIXME: Not yet implemented */
 }
 
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37))
@@ -294,12 +359,18 @@ IMG_VOID HostWaitForEvent(DBG_EVENT eEvent)
        switch(eEvent)
        {
                case DBG_EVENT_STREAM_DATA:
-                       
+                       /*
+                        * More than one process may be woken up.
+                        * Any process that wakes up should consume
+                        * all the data from the streams.
+                        */
                        wait_event_interruptible_timeout(sStreamDataEvent, iStreamData != 0, EVENT_WAIT_TIMEOUT_JIFFIES);
                        iStreamData = 0;
                        break;
                default:
-                       
+                       /*
+                        * For unknown events, enter an interruptible sleep.
+                        */
                        msleep_interruptible(EVENT_WAIT_TIMEOUT_MS);
                        break;
        }
@@ -321,4 +392,4 @@ IMG_VOID HostSignalEvent(DBG_EVENT eEvent)
 IMG_VOID HostDestroyEventObjects(IMG_VOID)
 {
 }
-#endif 
+#endif /* defined(SUPPORT_DBGDRV_EVENT_OBJECTS) */
index 6556249..c1ca85b 100644 (file)
@@ -1,29 +1,43 @@
-/**********************************************************************
- *
- * Copyright (C) Imagination Technologies Ltd. All rights reserved.
- * 
- * This program is free software; you can redistribute it and/or modify it
- * under the terms and conditions of the GNU General Public License,
- * version 2, as published by the Free Software Foundation.
- * 
- * This program is distributed in the hope it will be useful but, except 
- * as otherwise stated in writing, without any warranty; without even the 
- * implied warranty of merchantability or fitness for a particular purpose. 
- * See the GNU General Public License for more details.
- * 
- * You should have received a copy of the GNU General Public License along with
- * this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
- * 
- * The full GNU General Public License is included in this distribution in
- * the file called "COPYING".
- *
- * Contact Information:
- * Imagination Technologies Ltd. <gpl-support@imgtec.com>
- * Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK 
- *
- ******************************************************************************/
-
+/*************************************************************************/ /*!
+@Title          Debug driver main file
+@Copyright      Copyright (c) Imagination Technologies Ltd. All Rights Reserved
+@License        Dual MIT/GPLv2
+
+The contents of this file are subject to the MIT license as set out below.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+Alternatively, the contents of this file may be used under the terms of
+the GNU General Public License Version 2 ("GPL") in which case the provisions
+of GPL are applicable instead of those above.
+
+If you wish to allow use of your version of this file only under the terms of
+GPL, and not to allow others to use your version of this file under the terms
+of the MIT license, indicate your decision by deleting the provisions above
+and replace them with the notice and other provisions required by GPL as set
+out in the file called "GPL-COPYING" included in this distribution. If you do
+not delete the provisions above, a recipient may use your version of this file
+under the terms of either the MIT license or GPL.
+
+This License is also included in this distribution in the file called
+"MIT-COPYING".
+
+EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
+PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
+BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+*/ /**************************************************************************/
 #include <linux/errno.h>
 #include <linux/module.h>
 #include <linux/fs.h>
@@ -66,7 +80,7 @@
 #include "pvr_drm_shared.h"
 #include "pvr_drm.h"
 
-#else 
+#else /* defined(SUPPORT_DRI_DRM) */
 
 #define DRVNAME "dbgdrv"
 MODULE_SUPPORTED_DEVICE(DRVNAME);
@@ -102,11 +116,9 @@ static struct file_operations dbgdrv_fops = {
        .mmap           = dbgdrv_mmap,
 };
 
-#endif  
-
-IMG_VOID DBGDrvGetServiceTable(IMG_VOID **fn_table);
+#endif  /* defined(SUPPORT_DRI_DRM) */
 
-IMG_VOID DBGDrvGetServiceTable(IMG_VOID **fn_table)
+IMG_VOID DBGDrvGetServiceTable(DBGKM_SERVICE_TABLE **fn_table)
 {
        extern DBGKM_SERVICE_TABLE g_sDBGKMServices;
 
@@ -125,7 +137,7 @@ static void __exit dbgdrv_cleanup(void)
        class_destroy(psDbgDrvClass);
 #endif
        unregister_chrdev(AssignedMajorNumber, DRVNAME);
-#endif 
+#endif /* !defined(SUPPORT_DRI_DRM) */
 #if defined(SUPPORT_DBGDRV_EVENT_OBJECTS)
        HostDestroyEventObjects();
 #endif
@@ -147,14 +159,17 @@ static int __init dbgdrv_init(void)
        int err = -EBUSY;
 #endif
 
-       
+       /* Init API mutex */
        if ((g_pvAPIMutex=HostCreateMutex()) == IMG_NULL)
        {
                return -ENOMEM;
        }
 
 #if defined(SUPPORT_DBGDRV_EVENT_OBJECTS)
-       
+       /*
+        * The current implementation of HostCreateEventObjects on Linux
+        * can never fail, so there is no need to check for error.
+        */
        (void) HostCreateEventObjects();
 #endif
 
@@ -169,7 +184,10 @@ static int __init dbgdrv_init(void)
        }
 
 #if defined(LDM_PLATFORM) || defined(LDM_PCI)
-       
+       /*
+        * This code (using GPL symbols) facilitates automatic device
+        * node creation on platforms with udev (or similar).
+        */
        psDbgDrvClass = class_create(THIS_MODULE, DRVNAME);
        if (IS_ERR(psDbgDrvClass))
        {
@@ -189,8 +207,8 @@ static int __init dbgdrv_init(void)
                                                                __func__, PTR_ERR(psDev)));
                goto ErrDestroyClass;
        }
-#endif 
-#endif 
+#endif /* defined(LDM_PLATFORM) || defined(LDM_PCI) */
+#endif /* !defined(SUPPORT_DRI_DRM) */
 
        return 0;
 
@@ -206,7 +224,7 @@ ErrDestroyClass:
        class_destroy(psDbgDrvClass);
 #endif
        return err;
-#endif 
+#endif /* !defined(SUPPORT_DRI_DRM) */
 }
 
 #if defined(SUPPORT_DRI_DRM)
@@ -240,7 +258,7 @@ long dbgdrv_ioctl(struct file *file, unsigned int ioctlCmd, unsigned long arg)
                goto init_failed;
        }
 
-       
+       /* Extra -1 because ioctls start at DEBUG_SERVICE_IOCTL_BASE + 1 */
        cmd = MAKEIOCTLINDEX(pIP->ui32Cmd) - DEBUG_SERVICE_IOCTL_BASE - 1;
 
        if(pIP->ui32Cmd == DEBUG_SERVICE_READ)
@@ -297,11 +315,31 @@ init_failed:
 }
 
 
+/******************************************************************************
+ * Function Name: RemoveHotKey
+ *
+ * Inputs       : -
+ * Outputs      : -
+ * Returns      : -
+ * Globals Used : -
+ *
+ * Description  : Removes HotKey callbacks
+ *****************************************************************************/
 IMG_VOID RemoveHotKey (IMG_UINT32 hHotKey)
 {
        PVR_UNREFERENCED_PARAMETER(hHotKey);
 }
 
+/******************************************************************************
+ * Function Name: DefineHotKey
+ *
+ * Inputs       : -
+ * Outputs      : -
+ * Returns      : -
+ * Globals Used : -
+ *
+ * Description  : Removes HotKey callbacks
+ *****************************************************************************/
 IMG_VOID DefineHotKey (IMG_UINT32 ui32ScanCode, IMG_UINT32 ui32ShiftState, PHOTKEYINFO psInfo)
 {
        PVR_UNREFERENCED_PARAMETER(ui32ScanCode);