ScummVM API documentation
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Modules Pages
atari-graphics-supervidel.h
1 /* ScummVM - Graphic Adventure Engine
2  *
3  * ScummVM is the legal property of its developers, whose names
4  * are too numerous to list here. Please refer to the COPYRIGHT
5  * file distributed with this source distribution.
6  *
7  * This program is free software: you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation, either version 3 of the License, or
10  * (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program. If not, see <http://www.gnu.org/licenses/>.
19  *
20  */
21 
22 #ifndef BACKENDS_GRAPHICS_ATARI_SUPERVIDEL_H
23 #define BACKENDS_GRAPHICS_ATARI_SUPERVIDEL_H
24 
25 #ifdef USE_SUPERVIDEL
26 
27 #include "backends/graphics/atari/atari-graphics.h"
28 
29 #include <mint/osbind.h>
30 
31 #ifdef USE_SV_BLITTER
32 #include <mint/trap14.h>
33 #define ct60_vm(mode, value) (long)trap_14_wwl((short)0xc60e, (short)(mode), (long)(value))
34 #define ct60_vmalloc(value) ct60_vm(0, value)
35 #define ct60_vmfree(value) ct60_vm(1, value)
36 
37 #include "backends/platform/atari/dlmalloc.h"
38 extern mspace g_mspace;
39 #endif
40 
41 #include "backends/graphics/atari/atari-graphics-superblitter.h"
42 #include "backends/platform/atari/atari-debug.h"
43 #include "common/scummsys.h"
44 
45 class AtariSuperVidelManager : public AtariGraphicsManager {
46 public:
47  AtariSuperVidelManager() {
48 #ifdef USE_SV_BLITTER
49  atari_debug("SuperVidel FW Revision: %d, using %s", superVidelFwVersion, superVidelFwVersion >= 9
50  ? "fast async FIFO" : "slower sync blitting");
51 #else
52  atari_debug("SuperVidel FW Revision: %d, SuperBlitter not used", superVidelFwVersion);
53 #endif
54  if (Supexec(hasSvRamBoosted))
55  atari_debug("SV_XBIOS has the pmmu boost enabled");
56  else
57  atari_warning("SV_XBIOS has the pmmu boost disabled, set 'pmmu_boost = true' in C:\\SV.INF");
58 
59 #ifdef USE_SV_BLITTER
60  size_t vramSize = ct60_vmalloc(-1) - (16 * 1024 * 1024); // SV XBIOS seems to forget the initial 16 MB ST RAM mirror
61  _vramBase = vramSize > 0 ? (void *)ct60_vmalloc(vramSize) : nullptr;
62  if (_vramBase) {
63  g_mspace = create_mspace_with_base(_vramBase, vramSize, 0);
64  atari_debug("Allocated VRAM at %p (%ld bytes)", _vramBase, vramSize);
65  }
66 
67  if (!g_mspace)
68  atari_warning("VRAM allocation failed");
69 #endif
70  // using virtual methods so must be done here
71  allocateSurfaces();
72  }
73 
74  ~AtariSuperVidelManager() {
75  // using virtual methods so must be done here
76  freeSurfaces();
77 
78 #ifdef USE_SV_BLITTER
79  if (_vramBase) {
80  destroy_mspace(g_mspace);
81  g_mspace = nullptr;
82 
83  ct60_vmfree(_vramBase);
84  _vramBase = nullptr;
85  }
86 #endif
87  }
88 
89 private:
90  AtariMemAlloc getStRamAllocFunc() const override {
91  return [](size_t bytes) {
92  uintptr ptr = Mxalloc(bytes, MX_STRAM);
93 
94  if (ptr != 0)
95  ptr |= 0xA0000000;
96 
97  return (void*)ptr;
98  };
99  }
100  AtariMemFree getStRamFreeFunc() const override {
101  return [](void *ptr) { Mfree((uintptr)ptr & 0x00FFFFFF); };
102  }
103 
104  void drawMaskedSprite(Graphics::Surface &dstSurface, int dstBitsPerPixel,
105  const Graphics::Surface &srcSurface, const Graphics::Surface &srcMask,
106  int destX, int destY,
107  const Common::Rect &subRect) override {
108  assert(dstBitsPerPixel == 8);
109  assert(subRect.width() % 16 == 0);
110  assert(subRect.width() == srcSurface.w);
111 
112  const byte *src = (const byte *)srcSurface.getBasePtr(subRect.left, subRect.top);
113  const uint16 *mask = (const uint16 *)srcMask.getBasePtr(subRect.left, subRect.top);
114  byte *dst = (byte *)dstSurface.getBasePtr(destX, destY);
115 
116  const int h = subRect.height();
117  const int w = subRect.width();
118  const int dstOffset = dstSurface.pitch - w;
119 
120  for (int j = 0; j < h; ++j) {
121  for (int i = 0; i < w; i += 16, mask++) {
122  const uint16 m = *mask;
123 
124  if (m == 0xFFFF) {
125  // all 16 pixels transparentm6
126  src += 16;
127  dst += 16;
128  continue;
129  }
130 
131  for (int k = 0; k < 16; ++k) {
132  const uint16 bit = 1 << (15 - k);
133 
134  if (m & bit) {
135  // transparent
136  src++;
137  dst++;
138  } else {
139  *dst++ = *src++;
140  }
141  }
142  }
143 
144  dst += dstOffset;
145  }
146  }
147 
148  Common::Rect alignRect(int x, int y, int w, int h) const override {
149  return Common::Rect(x, y, x + w, y + h);
150  }
151 
152  static long hasSvRamBoosted() {
153  register long ret __asm__ ("d0") = 0;
154 
155  __asm__ volatile(
156  "\tmovec %%itt0,%%d1\n"
157  "\tcmp.l #0xA007E060,%%d1\n"
158  "\tbne.s 1f\n"
159 
160  "\tmovec %%dtt0,%%d1\n"
161  "\tcmp.l #0xA007E060,%%d1\n"
162  "\tbne.s 1f\n"
163 
164  "\tmoveq #1,%%d0\n"
165 
166  "1:\n"
167  : "=g"(ret) /* outputs */
168  : /* inputs */
169  : __CLOBBER_RETURN("d0") "d1", "cc"
170  );
171 
172  return ret;
173  }
174 
175 #ifdef USE_SV_BLITTER
176  void *_vramBase = nullptr;
177 #endif
178 };
179 
180 #endif // USE_SUPERVIDEL
181 
182 #endif
int32 pitch
Definition: surface.h:83
Definition: surface.h:67
Definition: rect.h:144
const void * getBasePtr(int x, int y) const
Definition: surface.h:138
int16 width() const
Definition: rect.h:192
int16 left
Definition: rect.h:145
int16 w
Definition: surface.h:71
Definition: atari-graphics.h:40
int16 height() const
Definition: rect.h:193