1 #include "lua/bitmap.hpp"
2 #include "lua/internal.hpp"
3 #include "library/serialization.hpp"
4 #include "library/memoryspace.hpp"
5 #include "core/instance.hpp"
6 #include "core/memorymanip.hpp"
10 template<bool create
, bool bpp2
>
11 int dump_sprite(lua::state
& L
, lua::parameters
& P
)
16 uint32_t width
, height
;
17 size_t stride1
= bpp2
? 16 : 32;
23 height
= b
->height
/ 8;
24 if((width
| height
) & 8)
25 throw std::runtime_error("The image size must be multiple of 8x8");
27 addr
= lua_get_read_address(P
);
30 P(P
.optional(stride2
, bpp2
? 256 : 512));
33 b
= lua::_class
<lua_bitmap
>::create(L
, width
* 8, height
* 8);
38 if(stride1
< (1 << 30) / (width
? width
: 1) && stride2
< (1 << 30) / (height
? height
: 1)) {
41 rangesize
= (width
- 1) * stride1
+ (height
- 1) * stride2
+ 32;
44 char* mem
= map
? core
.memory
->get_physical_mapping(rangebase
, rangesize
) : NULL
;
46 for(unsigned j
= 0; j
< height
; j
++)
47 for(unsigned i
= 0; i
< width
; i
++) {
48 uint64_t sbase
= addr
+ stride2
* j
+ stride1
* i
- rangebase
;
49 for(unsigned k
= 0; k
< 8; k
++) {
50 uint8_t byte1
= mem
[sbase
+ 2 * k
];
51 uint8_t byte2
= mem
[sbase
+ 2 * k
+ 1];
52 uint8_t byte3
= bpp2
? 0 : mem
[sbase
+ 2 * k
+ 16];
53 uint8_t byte4
= bpp2
? 0 : mem
[sbase
+ 2 * k
+ 17];
54 uint32_t soff
= (j
* 8 + k
) * (8 * width
) + i
* 8;
55 for(unsigned l
= 0; l
< 8; l
++) {
57 //No harm including the nonexistent planes (they are 0).
58 if((byte1
>> (7 - l
)) & 1) v
|= 1;
59 if((byte2
>> (7 - l
)) & 1) v
|= 2;
60 if((byte3
>> (7 - l
)) & 1) v
|= 4;
61 if((byte4
>> (7 - l
)) & 1) v
|= 8;
62 b
->pixels
[soff
+ l
] = v
;
67 for(unsigned j
= 0; j
< height
; j
++)
68 for(unsigned i
= 0; i
< width
; i
++) {
69 uint64_t sbase
= addr
+ stride2
* j
+ stride1
* i
;
70 for(unsigned k
= 0; k
< 8; k
++) {
71 uint8_t byte1
= core
.memory
->read
<uint8_t>(sbase
+ 2 * k
);
72 uint8_t byte2
= core
.memory
->read
<uint8_t>(sbase
+ 2 * k
+ 1);
73 uint8_t byte3
= bpp2
? 0 : core
.memory
->read
<uint8_t>(sbase
+ 2 * k
+
75 uint8_t byte4
= bpp2
? 0 : core
.memory
->read
<uint8_t>(sbase
+ 2 * k
+
77 uint32_t soff
= (j
* 8 + k
) * (8 * width
) + i
* 8;
78 for(unsigned l
= 0; l
< 8; l
++) {
79 //No harm including the nonexistent planes (they are 0).
81 if((byte1
>> (7 - l
)) & 1) v
|= 1;
82 if((byte2
>> (7 - l
)) & 1) v
|= 2;
83 if((byte3
>> (7 - l
)) & 1) v
|= 4;
84 if((byte4
>> (7 - l
)) & 1) v
|= 8;
85 b
->pixels
[soff
+ l
] = v
;
90 return create
? 1 : 0;
94 int dump_palette(lua::state
& L
, lua::parameters
& P
)
98 bool full
= false, ftrans
;
104 size_t ccount
= p
->color_count
;
105 if(ccount
!= 4 && ccount
!= 16 && ccount
!= 256)
106 throw std::runtime_error("Palette to read must be 4, 16 or 256 colors");
107 full
= (ccount
== 256);
108 fourcc
= (ccount
== 4);
110 addr
= lua_get_read_address(P
);
112 //Hacky way to do integers.
116 if(col
== 4) fourcc
= true;
118 else if(col
== 256) full
= true;
120 throw std::runtime_error("Palette to read must be 4, 16 or 256 colors");
127 size_t ps
= full
? 256 : (fourcc
? 4 : 16);
129 p
= lua::_class
<lua_palette
>::create(L
);
130 p
->adjust_palette_size(ps
);
132 uint8_t* mem
= reinterpret_cast<uint8_t*>(core
.memory
->get_physical_mapping(addr
, 2 * ps
));
134 for(unsigned j
= 0; j
< ps
; j
++) {
136 p
->colors
[j
] = framebuffer::color(-1);
139 uint16_t c
= serialization::u16l(mem
+ 2 * j
);
140 uint64_t r
= (c
>> 0) & 0x1F;
141 uint64_t g
= (c
>> 5) & 0x1F;
142 uint64_t b
= (c
>> 10) & 0x1F;
143 val
= (r
<< 19) | ((r
<< 14) & 0xFF0000) | (g
<< 11) | ((g
<< 6) & 0xFF00) |
145 p
->colors
[j
] = framebuffer::color(val
);
149 for(unsigned j
= 0; j
< ps
; j
++) {
151 p
->colors
[j
] = framebuffer::color(-1);
154 uint16_t c
= core
.memory
->read
<uint16_t>(addr
+ j
* 2);
155 uint64_t r
= (c
>> 0) & 0x1F;
156 uint64_t g
= (c
>> 5) & 0x1F;
157 uint64_t b
= (c
>> 10) & 0x1F;
158 val
= (r
<< 19) | ((r
<< 14) & 0xFF0000) | (g
<< 11) | ((g
<< 6) & 0xFF00) |
160 p
->colors
[j
] = framebuffer::color(val
);
164 return create
? 1 : 0;
167 lua::functions
bitmap_fns_snes(lua_func_misc
, "bsnes", {
168 {"dump_palette", dump_palette
<true>},
169 {"redump_palette", dump_palette
<false>},
170 {"dump_sprite", dump_sprite
<true, false>},
171 {"redump_sprite", dump_sprite
<false, false>},
172 {"dump_sprite2", dump_sprite
<true, true>},
173 {"redump_sprite2", dump_sprite
<false, true>},