Small fixes here and there.

Opti495SX machines are now limited to 32MB.
Cleaned up the CGA Composite code, it allocates on the heap now.
This commit is contained in:
waltje
2019-03-04 17:47:45 -05:00
parent d7a1c84b27
commit e8c527c4ef
10 changed files with 387 additions and 286 deletions

View File

@@ -11,7 +11,7 @@
* Version: @(#)808x.c 1.0.14 2019/02/28
*
* Authors: Miran Grca, <mgrca8@gmail.com>
* Andrew Jenner, <https://www.reenigne.org>
* Andrew Jenner (reenigne), <andrew@reenigne.org>
* Sarah Walker, <tommowalker@tommowalker.co.uk>
*
* Copyright 2016-2019 Fred N. van Kempen.

View File

@@ -8,7 +8,7 @@
*
* Emulation of the old and new IBM CGA graphics cards.
*
* Version: @(#)vid_cga.c 1.0.12 2019/03/03
* Version: @(#)vid_cga.c 1.0.12 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
@@ -171,7 +171,7 @@ cga_out(uint16_t port, uint8_t val, void *priv)
dev->cgamode = val;
if (old ^ val) {
if ((old ^ val) & 0x05)
update_cga16_color(val);
cga_comp_update(dev->cpriv, val);
cga_recalctimings(dev);
}
return;
@@ -462,8 +462,8 @@ cga_poll(void *priv)
else
border = dev->cgacol & 0x0f;
Composite_Process(dev->cgamode, border, x >> 2, buffer32->line[(dev->displine << 1)]);
Composite_Process(dev->cgamode, border, x >> 2, buffer32->line[(dev->displine << 1) + 1]);
cga_comp_process(dev->cpriv, dev->cgamode, border, x >> 2, buffer32->line[(dev->displine << 1)]);
cga_comp_process(dev->cpriv, dev->cgamode, border, x >> 2, buffer32->line[(dev->displine << 1) + 1]);
}
dev->sc = oldsc;
@@ -612,6 +612,10 @@ void
cga_init(cga_t *dev)
{
dev->composite = 0;
if (dev->cpriv != NULL) {
cga_comp_close(dev->cpriv);
dev->cpriv = NULL;
}
}
@@ -633,7 +637,7 @@ cga_standalone_init(const device_t *info)
dev->vram = (uint8_t *)mem_alloc(0x4000);
cga_comp_init(dev->revision);
dev->cpriv = cga_comp_init(dev->revision);
timer_add(cga_poll, &dev->vidtime, TIMER_ALWAYS_ENABLED, dev);
@@ -663,6 +667,10 @@ cga_close(void *priv)
cga_t *dev = (cga_t *)priv;
free(dev->vram);
if (dev->cpriv != NULL)
cga_comp_close(dev->cpriv);
free(dev);
}

View File

@@ -8,7 +8,7 @@
*
* Definitions for the CGA driver.
*
* Version: @(#)vid_cga.h 1.0.6 2019/03/01
* Version: @(#)vid_cga.h 1.0.7 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
@@ -78,10 +78,12 @@ typedef struct {
uint8_t charbuffer[256];
int revision;
int composite;
int snow_enabled;
int rgb_type;
int font_type;
int composite;
void *cpriv;
} cga_t;

View File

@@ -9,14 +9,20 @@
* IBM CGA composite filter, borrowed from reenigne's DOSBox
* patch and ported to C.
*
* Version: @(#)vid_cga_comp.c 1.0.5 2018/10/05
* New algorithm by reenigne.
* Works in all CGA modes/color settings and can simulate
* older and newer CGA revisions.
*
* Reworked to have its data on the heap.
*
* Version: @(#)vid_cga_comp.c 1.0.6 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
* reengine,
* Andrew Jenner (reenigne), <andrew@reenigne.org>
*
* Copyright 2017,2018 Fred N. van Kempen.
* Copyright 2015-2018 reenigne.
* Copyright 2017-2019 Fred N. van Kempen.
* Copyright 2015-2018 Andrew Jenner.
* Copyright 2016-2018 Miran Grca.
*
* This program is free software; you can redistribute it and/or modify
@@ -50,158 +56,78 @@
#include "vid_cga_comp.h"
int CGA_Composite_Table[1024];
static double brightness = 0;
static double contrast = 100;
static double saturation = 100;
static double sharpness = 0;
static double hue_offset = 0;
/* New algorithm by reenigne
Works in all CGA modes/color settings and can simulate older and newer CGA revisions */
static const double tau = 6.28318531; /* == 2*pi */
static unsigned char chroma_multiplexer[256] = {
2, 2, 2, 2, 114,174, 4, 3, 2, 1,133,135, 2,113,150, 4,
133, 2, 1, 99, 151,152, 2, 1, 3, 2, 96,136, 151,152,151,152,
2, 56, 62, 4, 111,250,118, 4, 0, 51,207,137, 1,171,209, 5,
140, 50, 54,100, 133,202, 57, 4, 2, 50,153,149, 128,198,198,135,
32, 1, 36, 81, 147,158, 1, 42, 33, 1,210,254, 34,109,169, 77,
177, 2, 0,165, 189,154, 3, 44, 33, 0, 91,197, 178,142,144,192,
4, 2, 61, 67, 117,151,112, 83, 4, 0,249,255, 3,107,249,117,
147, 1, 50,162, 143,141, 52, 54, 3, 0,145,206, 124,123,192,193,
72, 78, 2, 0, 159,208, 4, 0, 53, 58,164,159, 37,159,171, 1,
248,117, 4, 98, 212,218, 5, 2, 54, 59, 93,121, 176,181,134,130,
1, 61, 31, 0, 160,255, 34, 1, 1, 58,197,166, 0,177,194, 2,
162,111, 34, 96, 205,253, 32, 1, 1, 57,123,125, 119,188,150,112,
78, 4, 0, 75, 166,180, 20, 38, 78, 1,143,246, 42,113,156, 37,
252, 4, 1,188, 175,129, 1, 37, 118, 4, 88,249, 202,150,145,200,
61, 59, 60, 60, 228,252,117, 77, 60, 58,248,251, 81,212,254,107,
198, 59, 58,169, 250,251, 81, 80, 100, 58,154,250, 251,252,252,252};
static double intensity[4] = {
77.175381, 88.654656, 166.564623, 174.228438};
static const uint8_t chroma_multiplexer[256] = {
2, 2, 2, 2, 114,174, 4, 3, 2, 1,133,135, 2,113,150, 4,
133, 2, 1, 99, 151,152, 2, 1, 3, 2, 96,136, 151,152,151,152,
2, 56, 62, 4, 111,250,118, 4, 0, 51,207,137, 1,171,209, 5,
140, 50, 54,100, 133,202, 57, 4, 2, 50,153,149, 128,198,198,135,
32, 1, 36, 81, 147,158, 1, 42, 33, 1,210,254, 34,109,169, 77,
177, 2, 0,165, 189,154, 3, 44, 33, 0, 91,197, 178,142,144,192,
4, 2, 61, 67, 117,151,112, 83, 4, 0,249,255, 3,107,249,117,
147, 1, 50,162, 143,141, 52, 54, 3, 0,145,206, 124,123,192,193,
72, 78, 2, 0, 159,208, 4, 0, 53, 58,164,159, 37,159,171, 1,
248,117, 4, 98, 212,218, 5, 2, 54, 59, 93,121, 176,181,134,130,
1, 61, 31, 0, 160,255, 34, 1, 1, 58,197,166, 0,177,194, 2,
162,111, 34, 96, 205,253, 32, 1, 1, 57,123,125, 119,188,150,112,
78, 4, 0, 75, 166,180, 20, 38, 78, 1,143,246, 42,113,156, 37,
252, 4, 1,188, 175,129, 1, 37, 118, 4, 88,249, 202,150,145,200,
61, 59, 60, 60, 228,252,117, 77, 60, 58,248,251, 81,212,254,107,
198, 59, 58,169, 250,251, 81, 80, 100, 58,154,250, 251,252,252,252
};
static const double intensity[4] = {
77.175381, 88.654656, 166.564623, 174.228438
};
#define NEW_CGA(c,i,r,g,b) (((c)/0.72)*0.29 + ((i)/0.28)*0.32 + ((r)/0.28)*0.1 + ((g)/0.28)*0.22 + ((b)/0.28)*0.07)
double mode_brightness;
double mode_contrast;
double mode_hue;
double min_v;
double max_v;
double video_ri, video_rq, video_gi, video_gq, video_bi, video_bq;
int video_sharpness;
int tandy_mode_control = 0;
static bool new_cga = 0;
void update_cga16_color(uint8_t cgamode) {
int x;
double c, i, v;
double q, a, s, r;
double iq_adjust_i, iq_adjust_q;
double i0, i3, mode_saturation;
static const double ri = 0.9563;
static const double rq = 0.6210;
static const double gi = -0.2721;
static const double gq = -0.6474;
static const double bi = -1.1069;
static const double bq = 1.7046;
if (!new_cga) {
min_v = chroma_multiplexer[0] + intensity[0];
max_v = chroma_multiplexer[255] + intensity[3];
}
else {
i0 = intensity[0];
i3 = intensity[3];
min_v = NEW_CGA(chroma_multiplexer[0], i0, i0, i0, i0);
max_v = NEW_CGA(chroma_multiplexer[255], i3, i3, i3, i3);
}
mode_contrast = 256/(max_v - min_v);
mode_brightness = -min_v*mode_contrast;
if ((cgamode & 3) == 1)
mode_hue = 14;
else
mode_hue = 4;
mode_contrast *= contrast * (new_cga ? 1.2 : 1)/100; /* new CGA: 120% */
mode_brightness += (new_cga ? brightness-10 : brightness)*5; /* new CGA: -10 */
mode_saturation = (new_cga ? 4.35 : 2.9)*saturation/100; /* new CGA: 150% */
for (x = 0; x < 1024; ++x) {
int phase = x & 3;
int right = (x >> 2) & 15;
int left = (x >> 6) & 15;
int rc = right;
int lc = left;
if ((cgamode & 4) != 0) {
rc = (right & 8) | ((right & 7) != 0 ? 7 : 0);
lc = (left & 8) | ((left & 7) != 0 ? 7 : 0);
}
c = chroma_multiplexer[((lc & 7) << 5) | ((rc & 7) << 2) | phase];
i = intensity[(left >> 3) | ((right >> 2) & 2)];
if (!new_cga)
v = c + i;
else {
double d_r = intensity[((left >> 2) & 1) | ((right >> 1) & 2)];
double d_g = intensity[((left >> 1) & 1) | (right & 2)];
double d_b = intensity[(left & 1) | ((right << 1) & 2)];
v = NEW_CGA(c, i, d_r, d_g, d_b);
}
CGA_Composite_Table[x] = (int) (v*mode_contrast + mode_brightness);
}
i = CGA_Composite_Table[6*68] - CGA_Composite_Table[6*68 + 2];
q = CGA_Composite_Table[6*68 + 1] - CGA_Composite_Table[6*68 + 3];
a = tau*(33 + 90 + hue_offset + mode_hue)/360.0;
c = cos(a);
s = sin(a);
r = 256*mode_saturation/sqrt(i*i+q*q);
iq_adjust_i = -(i*c + q*s)*r;
iq_adjust_q = (q*c - i*s)*r;
video_ri = (int) (ri*iq_adjust_i + rq*iq_adjust_q);
video_rq = (int) (-ri*iq_adjust_q + rq*iq_adjust_i);
video_gi = (int) (gi*iq_adjust_i + gq*iq_adjust_q);
video_gq = (int) (-gi*iq_adjust_q + gq*iq_adjust_i);
video_bi = (int) (bi*iq_adjust_i + bq*iq_adjust_q);
video_bq = (int) (-bi*iq_adjust_q + bq*iq_adjust_i);
video_sharpness = (int) (sharpness*256/100);
}
static Bit8u byte_clamp(int v) {
v >>= 13;
return v < 0 ? 0 : (v > 255 ? 255 : v);
}
/* 2048x1536 is the maximum we can possibly support. */
#define SCALER_MAXWIDTH 2048
static int temp[SCALER_MAXWIDTH + 10]={0};
static int atemp[SCALER_MAXWIDTH + 2]={0};
static int btemp[SCALER_MAXWIDTH + 2]={0};
Bit8u * Composite_Process(uint8_t cgamode, Bit8u border, Bit32u blocks/*, bool doublewidth*/, Bit8u *TempLine)
typedef struct {
int new_cga;
int video_sharpness;
double mode_brightness,
mode_contrast,
mode_hue,
min_v, max_v;
double video_ri, video_rq, video_gi,
video_gq, video_bi, video_bq;
double brightness,
contrast,
saturation,
sharpness,
hue_offset;
int temp[SCALER_MAXWIDTH + 10];
int atemp[SCALER_MAXWIDTH + 2];
int btemp[SCALER_MAXWIDTH + 2];
int table[1024];
} cga_comp_t;
static uint8_t
byte_clamp(int v)
{
int x;
Bit32u x2;
v >>= 13;
int w = blocks*4;
return v < 0 ? 0 : (v > 255 ? 255 : v);
}
int *o;
Bit8u *rgbi;
int *b2;
int *i;
Bit32u* srgb;
int *ap, *bp;
uint8_t *
cga_comp_process(void *priv, uint8_t cgamode, uint8_t border,
uint32_t blocks/*, int8_t doublewidth*/, uint8_t *TempLine)
{
cga_comp_t *state = (cga_comp_t *)priv;
uint32_t x2, *srgb;
int x, w = blocks*4;
int *o, *b2, *i, *ap, *bp;
uint8_t *rgbi;
#define COMPOSITE_CONVERT(I, Q) do { \
i[1] = (i[1]<<3) - ap[1]; \
@@ -209,157 +135,294 @@ Bit8u * Composite_Process(uint8_t cgamode, Bit8u border, Bit32u blocks/*, bool d
b = bp[0]; \
c = i[0]+i[0]; \
d = i[-1]+i[1]; \
y = ((c+d)<<8) + video_sharpness*(c-d); \
rr = (int)(y + video_ri*(I) + video_rq*(Q)); \
gg = (int)(y + video_gi*(I) + video_gq*(Q)); \
bb = (int)(y + video_bi*(I) + video_bq*(Q)); \
y = ((c+d)<<8) + state->video_sharpness*(c-d); \
rr = (int)(y + state->video_ri*(I) + state->video_rq*(Q)); \
gg = (int)(y + state->video_gi*(I) + state->video_gq*(Q)); \
bb = (int)(y + state->video_bi*(I) + state->video_bq*(Q)); \
++i; \
++ap; \
++bp; \
*srgb = (byte_clamp(rr)<<16) | (byte_clamp(gg)<<8) | byte_clamp(bb); \
++srgb; \
} while (0)
} while (0)
#define OUT(v) do { *o = (v); ++o; } while (0)
/* Simulate CGA composite output */
o = temp;
rgbi = TempLine;
b2 = &CGA_Composite_Table[border*68];
for (x = 0; x < 4; ++x)
OUT(b2[(x+3)&3]);
OUT(CGA_Composite_Table[(border<<6) | ((*rgbi)<<2) | 3]);
for (x = 0; x < w-1; ++x) {
OUT(CGA_Composite_Table[(rgbi[0]<<6) | (rgbi[1]<<2) | (x&3)]);
++rgbi;
}
OUT(CGA_Composite_Table[((*rgbi)<<6) | (border<<2) | 3]);
for (x = 0; x < 5; ++x)
OUT(b2[x&3]);
/* Simulate CGA composite output. */
o = state->temp;
rgbi = TempLine;
b2 = &state->table[border * 68];
for (x = 0; x < 4; ++x)
OUT(b2[(x+3)&3]);
OUT(state->table[(border<<6) | ((*rgbi)<<2) | 3]);
if ((cgamode & 4) != 0) {
/* Decode */
i = temp + 5;
srgb = (Bit32u *)TempLine;
for (x2 = 0; x2 < blocks*4; ++x2) {
int c = (i[0]+i[0])<<3;
int d = (i[-1]+i[1])<<3;
int y = ((c+d)<<8) + video_sharpness*(c-d);
++i;
*srgb = byte_clamp(y)*0x10101;
++srgb;
}
}
else {
/* Store chroma */
i = temp + 4;
ap = atemp + 1;
bp = btemp + 1;
for (x = -1; x < w + 1; ++x) {
ap[x] = i[-4]-((i[-2]-i[0]+i[2])<<1)+i[4];
bp[x] = (i[-3]-i[-1]+i[1]-i[3])<<1;
++i;
}
for (x = 0; x < w-1; ++x) {
OUT(state->table[(rgbi[0]<<6) | (rgbi[1]<<2) | (x&3)]);
++rgbi;
}
OUT(state->table[((*rgbi)<<6) | (border<<2) | 3]);
/* Decode */
i = temp + 5;
i[-1] = (i[-1]<<3) - ap[-1];
i[0] = (i[0]<<3) - ap[0];
srgb = (Bit32u *)TempLine;
for (x2 = 0; x2 < blocks; ++x2) {
int y,a,b,c,d,rr,gg,bb;
COMPOSITE_CONVERT(a, b);
COMPOSITE_CONVERT(-b, a);
COMPOSITE_CONVERT(-a, -b);
COMPOSITE_CONVERT(b, -a);
}
}
#undef COMPOSITE_CONVERT
#undef OUT
for (x = 0; x < 5; ++x)
OUT(b2[x&3]);
return TempLine;
if ((cgamode & 4) != 0) {
/* Decode. */
i = state->temp + 5;
srgb = (uint32_t *)TempLine;
for (x2 = 0; x2 < blocks*4; ++x2) {
int c = (i[0]+i[0])<<3;
int d = (i[-1]+i[1])<<3;
int y = ((c+d)<<8) + state->video_sharpness*(c-d);
++i;
*srgb = byte_clamp(y)*0x10101;
++srgb;
}
} else {
/* Store chroma. */
i = state->temp + 4;
ap = state->atemp + 1;
bp = state->btemp + 1;
for (x = -1; x < w + 1; ++x) {
ap[x] = i[-4]-((i[-2]-i[0]+i[2])<<1)+i[4];
bp[x] = (i[-3]-i[-1]+i[1]-i[3])<<1;
++i;
}
/* Decode. */
i = state->temp + 5;
i[-1] = (i[-1]<<3) - ap[-1];
i[0] = (i[0]<<3) - ap[0];
srgb = (uint32_t *)TempLine;
for (x2 = 0; x2 < blocks; ++x2) {
int y,a,b,c,d,rr,gg,bb;
COMPOSITE_CONVERT(a, b);
COMPOSITE_CONVERT(-b, a);
COMPOSITE_CONVERT(-a, -b);
COMPOSITE_CONVERT(b, -a);
}
}
return TempLine;
}
void IncreaseHue(uint8_t cgamode)
void
cga_comp_update(void *priv, uint8_t cgamode)
{
hue_offset += 5.0;
static const double ri = 0.9563;
static const double rq = 0.6210;
static const double gi = -0.2721;
static const double gq = -0.6474;
static const double bi = -1.1069;
static const double bq = 1.7046;
cga_comp_t *state = (cga_comp_t *)priv;
double iq_adjust_i, iq_adjust_q;
double i0, i3, mode_saturation;
double q, a, s, r;
double c, i, v;
int x;
update_cga16_color(cgamode);
if (state->new_cga) {
i0 = intensity[0];
i3 = intensity[3];
state->min_v = NEW_CGA(chroma_multiplexer[0], i0, i0, i0, i0);
state->max_v = NEW_CGA(chroma_multiplexer[255], i3, i3, i3, i3);
} else {
state->min_v = chroma_multiplexer[0] + intensity[0];
state->max_v = chroma_multiplexer[255] + intensity[3];
}
state->mode_contrast = 256 / (state->max_v - state->min_v);
state->mode_brightness = -state->min_v * state->mode_contrast;
if ((cgamode & 3) == 1)
state->mode_hue = 14;
else
state->mode_hue = 4;
state->mode_contrast *= state->contrast * (state->new_cga ? 1.2 : 1)/100; /* new CGA: 120% */
state->mode_brightness += (state->new_cga ? state->brightness-10 : state->brightness)*5; /* new CGA: -10 */
mode_saturation = (state->new_cga ? 4.35 : 2.9)*state->saturation/100; /* new CGA: 150% */
for (x = 0; x < 1024; ++x) {
int phase = x & 3;
int right = (x >> 2) & 15;
int left = (x >> 6) & 15;
int rc = right;
int lc = left;
if ((cgamode & 4) != 0) {
rc = (right & 8) | ((right & 7) != 0 ? 7 : 0);
lc = (left & 8) | ((left & 7) != 0 ? 7 : 0);
}
c = chroma_multiplexer[((lc & 7) << 5) | ((rc & 7) << 2) | phase];
i = intensity[(left >> 3) | ((right >> 2) & 2)];
if (state->new_cga) {
double d_r = intensity[((left >> 2) & 1) | ((right >> 1) & 2)];
double d_g = intensity[((left >> 1) & 1) | (right & 2)];
double d_b = intensity[(left & 1) | ((right << 1) & 2)];
v = NEW_CGA(c, i, d_r, d_g, d_b);
} else
v = c + i;
state->table[x] = (int) (v*state->mode_contrast + state->mode_brightness);
}
i = state->table[6*68] - state->table[6*68 + 2];
q = state->table[6*68 + 1] - state->table[6*68 + 3];
a = tau*(33 + 90 + state->hue_offset + state->mode_hue)/360.0;
c = cos(a);
s = sin(a);
r = 256*mode_saturation/sqrt(i*i+q*q);
iq_adjust_i = -(i*c + q*s)*r;
iq_adjust_q = (q*c - i*s)*r;
state->video_ri = (int) (ri * iq_adjust_i + rq * iq_adjust_q);
state->video_rq = (int) (-ri * iq_adjust_q + rq * iq_adjust_i);
state->video_gi = (int) (gi * iq_adjust_i + gq * iq_adjust_q);
state->video_gq = (int) (-gi * iq_adjust_q + gq * iq_adjust_i);
state->video_bi = (int) (bi * iq_adjust_i + bq * iq_adjust_q);
state->video_bq = (int) (-bi * iq_adjust_q + bq * iq_adjust_i);
state->video_sharpness = (int) ((state->sharpness * 256) / 100);
}
void DecreaseHue(uint8_t cgamode)
void *
cga_comp_init(int revision)
{
hue_offset -= 5.0;
cga_comp_t *state;
update_cga16_color(cgamode);
state = (cga_comp_t *)mem_alloc(sizeof(cga_comp_t));
memset(state, 0x00, sizeof(cga_comp_t));
state->new_cga = revision;
/* Making sure this gets reset after reset. */
state->contrast = 100;
state->saturation = 100;
cga_comp_update(state, 0);
return(state);
}
void IncreaseSaturation(uint8_t cgamode)
void
cga_comp_close(void *priv)
{
saturation += 5;
cga_comp_t *state = (cga_comp_t *)priv;
update_cga16_color(cgamode);
free(state);
}
void DecreaseSaturation(uint8_t cgamode)
#if 0 /*NOT_USED*/
void
IncreaseHue(void *priv, uint8_t cgamode)
{
saturation -= 5;
cga_comp_t *state = (cga_comp_t *)priv;
update_cga16_color(cgamode);
state->hue_offset += 5.0;
cga_comp_update(state, cgamode);
}
void IncreaseContrast(uint8_t cgamode)
void
DecreaseHue(void *priv, uint8_t cgamode)
{
contrast += 5;
cga_comp_t *state = (cga_comp_t *)priv;
update_cga16_color(cgamode);
state->hue_offset -= 5.0;
cga_comp_update(state, cgamode);
}
void DecreaseContrast(uint8_t cgamode)
void
IncreaseSaturation(void *priv, uint8_t cgamode)
{
contrast -= 5;
cga_comp_t *state = (cga_comp_t *)priv;
update_cga16_color(cgamode);
state->saturation += 5;
cga_comp_update(state, cgamode);
}
void IncreaseBrightness(uint8_t cgamode)
void
DecreaseSaturation(void *priv, uint8_t cgamode)
{
brightness += 5;
cga_comp_t *state = (cga_comp_t *)priv;
update_cga16_color(cgamode);
state->saturation -= 5;
cga_comp_update(state, cgamode);
}
void DecreaseBrightness(uint8_t cgamode)
void
IncreaseContrast(void *priv, uint8_t cgamode)
{
brightness -= 5;
cga_comp_t *state = (cga_comp_t *)priv;
update_cga16_color(cgamode);
state->contrast += 5;
cga_comp_update(state, cgamode);
}
void IncreaseSharpness(uint8_t cgamode)
void
DecreaseContrast(void *priv, uint8_t cgamode)
{
sharpness += 10;
cga_comp_t *state = (cga_comp_t *)priv;
update_cga16_color(cgamode);
state->contrast -= 5;
cga_comp_update(state, cgamode);
}
void DecreaseSharpness(uint8_t cgamode)
void
IncreaseBrightness(void *priv, uint8_t cgamode)
{
sharpness -= 10;
cga_comp_t *state = (cga_comp_t *)priv;
update_cga16_color(cgamode);
state->brightness += 5;
cga_comp_update(state, cgamode);
}
void cga_comp_init(int revision)
void
DecreaseBrightness(void *priv, uint8_t cgamode)
{
new_cga = revision;
cga_comp_t *state = (cga_comp_t *)priv;
/* Making sure this gets reset after reset. */
brightness = 0;
contrast = 100;
saturation = 100;
sharpness = 0;
hue_offset = 0;
state->brightness -= 5;
update_cga16_color(0);
cga_comp_update(state, cgamode);
}
void
IncreaseSharpness(void *priv, uint8_t cgamode)
{
cga_comp_t *state = (cga_comp_t *)priv;
state->sharpness += 10;
cga_comp_update(state, cgamode);
}
void
DecreaseSharpness(void *priv, uint8_t cgamode)
{
cga_comp_t *state = (cga_comp_t *)priv;
state->sharpness -= 10;
cga_comp_update(state, cgamode);
}
#endif /*NOT_USED*/

View File

@@ -8,13 +8,13 @@
*
* Definitions for the IBM CGA composite filter.
*
* Version: @(#)vid_cga_comp.h 1.0.1 2018/02/14
* Version: @(#)vid_cga_comp.h 1.0.2 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
* reengine,
* Andrew Jenner (reenigne), <andrew@reenigne.org>
*
* Copyright 2017,2018 Fred N. van Kempen.
* Copyright 2017-2019 Fred N. van Kempen.
* Copyright 2016-2018 Miran Grca.
*
* This program is free software; you can redistribute it and/or modify
@@ -39,14 +39,13 @@
# define VIDEO_CGA_COMP_H
#define Bit8u uint8_t
#define Bit32u uint32_t
#define Bitu unsigned int
#define bool uint8_t
extern void *cga_comp_init(int revision);
extern void cga_comp_close(void *);
void update_cga16_color(uint8_t cgamode);
void cga_comp_init(int revision);
Bit8u * Composite_Process(uint8_t cgamode, Bit8u border, Bit32u blocks/*, bool doublewidth*/, Bit8u *TempLine);
extern void cga_comp_update(void *, uint8_t cgamode);
extern uint8_t *cga_comp_process(void *, uint8_t cgamode, uint8_t border,
uint32_t blocks, /*int8_t doublewidth,*/
uint8_t *TempLine);
#endif /*VIDEO_CGA_COMP_H*/

View File

@@ -8,7 +8,7 @@
*
* Implementation of CGA used by Compaq PC's.
*
* Version: @(#)vid_cga_compaq.c 1.0.5 2019/02/10
* Version: @(#)vid_cga_compaq.c 1.0.6 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
@@ -112,7 +112,7 @@ compaq_poll(void *priv)
oldsc = dev->cga.sc;
if ((dev->cga.crtc[8] & 3) == 3)
dev->cga.sc = ((dev->cga.sc << 1) + dev->cga.oddeven) & 7;
dev->cga.sc = ((dev->cga.sc << 1) + dev->cga.oddeven) & 7;
if (dev->cga.cgadispon) {
if (dev->cga.displine < dev->cga.firstline) {
@@ -120,7 +120,7 @@ compaq_poll(void *priv)
video_wait_for_buffer();
}
dev->cga.lastline = dev->cga.displine;
cols[0] = (dev->cga.cgacol & 15);
for (c = 0; c < 8; c++) {
@@ -232,9 +232,9 @@ compaq_poll(void *priv)
buffer32->line[dev->cga.displine][c] = ((uint32_t *)buffer32->line[dev->cga.displine])[c] & 0xf;
if (dev->flags)
Composite_Process(dev->cga.cgamode & 0x7F, 0, x >> 2, buffer32->line[dev->cga.displine]);
cga_comp_process(dev->cga.cpriv, dev->cga.cgamode & 0x7F, 0, x >> 2, buffer32->line[dev->cga.displine]);
else
Composite_Process(dev->cga.cgamode, 0, x >> 2, buffer32->line[dev->cga.displine]);
cga_comp_process(dev->cga.cpriv, dev->cga.cgamode, 0, x >> 2, buffer32->line[dev->cga.displine]);
} else {
for (c = 0; c < x; c++)
buffer->line[dev->cga.displine][c] = ((uint32_t *)buffer32->line[dev->cga.displine])[c];
@@ -381,7 +381,7 @@ compaq_cga_init(const device_t *info)
dev->cga.vram = (uint8_t *)mem_alloc(0x4000);
cga_comp_init(dev->cga.revision);
dev->cga.cpriv = cga_comp_init(dev->cga.revision);
timer_add(compaq_poll, &dev->cga.vidtime, TIMER_ALWAYS_ENABLED, dev);
@@ -432,7 +432,11 @@ compaq_cga_close(void *priv)
{
compaq_cga_t *dev = (compaq_cga_t *)priv;
if (dev->cga.cpriv != NULL)
cga_comp_close(dev->cga.cpriv);
free(dev->cga.vram);
free(dev);
}

View File

@@ -8,13 +8,13 @@
*
* Plantronics ColorPlus emulation.
*
* Version: @(#)vid_colorplus.c 1.0.9 2018/11/11
* Version: @(#)vid_colorplus.c 1.0.10 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
* Sarah Walker, <tommowalker@tommowalker.co.uk>
*
* Copyright 2017,2018 Fred N. van Kempen.
* Copyright 2017-2019 Fred N. van Kempen.
* Copyright 2016-2018 Miran Grca.
* Copyright 2008-2018 Sarah Walker.
*
@@ -251,7 +251,7 @@ colorplus_poll(void *priv)
for (c = 0; c < x; c++)
buffer32->line[dev->cga.displine][c] = buffer->line[dev->cga.displine][c] & 0xf;
Composite_Process(dev->cga.cgamode, 0, x >> 2, buffer32->line[dev->cga.displine]);
cga_comp_process(dev->cga.cpriv, dev->cga.cgamode, 0, x >> 2, buffer32->line[dev->cga.displine]);
}
dev->cga.sc = oldsc;
@@ -395,8 +395,8 @@ colorplus_init(const device_t *info)
dev->cga.snow_enabled = device_get_config_int("snow_enabled");
dev->cga.vram = (uint8_t *)mem_alloc(0x8000);
cga_comp_init(1);
dev->cga.cpriv = cga_comp_init(1);
timer_add(colorplus_poll, &dev->cga.vidtime, TIMER_ALWAYS_ENABLED, dev);
@@ -422,7 +422,11 @@ colorplus_close(void *priv)
{
colorplus_t *dev = (colorplus_t *)priv;
if (dev->cga.cpriv != NULL)
cga_comp_close(dev->cga.cpriv);
free(dev->cga.vram);
free(dev);
}

View File

@@ -8,7 +8,7 @@
*
* Emulation of the IBM PCjr.
*
* Version: @(#)m_pcjr.c 1.0.13 2019/02/16
* Version: @(#)m_pcjr.c 1.0.14 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
@@ -102,6 +102,7 @@ typedef struct {
int64_t dispontime, dispofftime, vidtime;
int firstline, lastline;
int composite;
void *cpriv;
/* Keyboard Controller stuff. */
int latched;
@@ -188,7 +189,7 @@ vid_out(uint16_t addr, uint8_t val, void *p)
val &= 0x0f;
pcjr->array[pcjr->array_index & 0x1f] = val;
if (!(pcjr->array_index & 0x1f))
update_cga16_color(val);
cga_comp_update(pcjr->cpriv, val);
}
pcjr->array_ff = !pcjr->array_ff;
break;
@@ -460,7 +461,7 @@ vid_poll(void *p)
for (c = 0; c < x; c++)
buffer32->line[pcjr->displine][c] = buffer->line[pcjr->displine][c] & 0xf;
Composite_Process(pcjr->array[0], 0, x >> 2, buffer32->line[pcjr->displine]);
cga_comp_process(pcjr->cpriv, pcjr->array[0], 0, x >> 2, buffer32->line[pcjr->displine]);
}
pcjr->sc = oldsc;
if (pcjr->vc == pcjr->crtc[7] && !pcjr->sc) {
@@ -706,6 +707,18 @@ kbd_adddata_ex(uint16_t val)
}
static void
pcjr_close(void *priv)
{
pcjr_t *pcjr = (pcjr_t *)priv;
if (pcjr->composite && pcjr->cpriv)
cga_comp_close(pcjr->cpriv);
free(pcjr);
}
static void
speed_changed(void *priv)
{
@@ -741,7 +754,7 @@ static const video_timings_t pcjr_timings = { VID_BUS,0,0,0,0,0,0 };
const device_t m_pcjr_device = {
"IBM PCjr",
0, 0,
NULL, NULL, NULL,
NULL, pcjr_close, NULL,
NULL,
speed_changed,
NULL,
@@ -761,6 +774,8 @@ m_pcjr_init(const machine_t *model, UNUSED(void *arg))
dev->memctrl = -1;
display_type = machine_get_config_int("display_type");
dev->composite = (display_type != PCJR_RGB);
if (dev->composite)
dev->cpriv = cga_comp_init(0);
pic_init();
pit_init();

View File

@@ -11,7 +11,7 @@
* NOTE: It might be better (after all..) to split off the video
* driver from the main code, to keep it a little cleaner.
*
* Version: @(#)m_tandy.c 1.0.15 2019/02/16
* Version: @(#)m_tandy.c 1.0.16 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
@@ -116,6 +116,7 @@ typedef struct {
lastline;
int composite;
void *cpriv;
} t1kvid_t;
typedef struct {
@@ -554,7 +555,7 @@ vid_out(uint16_t addr, uint8_t val, void *priv)
case 0x03d8:
vid->mode = val;
if (dev->type != 2)
update_cga16_color(vid->mode);
cga_comp_update(vid->cpriv, vid->mode);
break;
case 0x03d9:
@@ -879,7 +880,7 @@ vid_poll(void *priv)
for (c = 0; c < x; c++)
buffer32->line[vid->displine][c] = buffer->line[vid->displine][c] & 0xf;
Composite_Process(vid->mode, 0, x >> 2, buffer32->line[vid->displine]);
cga_comp_process(vid->cpriv, vid->mode, 0, x >> 2, buffer32->line[vid->displine]);
}
vid->sc = oldsc;
if (vid->vc == vid->crtc[7] && !vid->sc)
@@ -1355,6 +1356,12 @@ static void
vid_close(void *priv)
{
tandy_t *dev = (tandy_t *)priv;
t1kvid_t *vid = dev->vid;
if (vid->cpriv != NULL) {
cga_comp_close(vid->cpriv);
vid->cpriv = NULL;
}
free(dev->vid);
dev->vid = NULL;
@@ -1374,8 +1381,7 @@ vid_init(tandy_t *dev)
display_type = machine_get_config_int("display_type");
vid->composite = (display_type != TANDY_RGB);
cga_comp_init(1);
vid->cpriv = cga_comp_init(1);
if (dev->type == 2) {
vid->b8000_limit = 0x8000;

View File

@@ -8,7 +8,7 @@
*
* Handling of the emulated machines.
*
* Version: @(#)machine_table.c 1.0.35 2019/03/03
* Version: @(#)machine_table.c 1.0.36 2019/03/04
*
* Authors: Fred N. van Kempen, <decwiz@yahoo.com>
* Miran Grca, <mgrca8@gmail.com>
@@ -137,9 +137,9 @@ const machine_t machines[] = {
{ "[386SX MCA] IBM PS/2 model 55SX", "ibm_ps2_m55sx", L"ibm/ps2_m55sx", 16, {{"Intel", cpus_i386SX}, {"AMD", cpus_Am386SX}, {"Cyrix", cpus_486SLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_MCA | MACHINE_AT | MACHINE_PS2 | MACHINE_VIDEO | MACHINE_HDC_PS2, 1, 8, 1, 64, m_ps2_model_55sx_init, NULL, NULL },
/* 80386DX */
{ "[386DX ISA] AMI 386DX (Opti495)", "ami_386dx_opti495", L"opti495/ami", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_AT | MACHINE_HDC, 1, 64, 1, 128, m_at_opti495_ami_init, NULL, NULL },
{ "[386DX ISA] Award 386DX (Opti495)", "award_386dx_opti495", L"opti495/award", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_AT | MACHINE_HDC, 1, 64, 1, 128, m_at_opti495_award_init, NULL, NULL },
{ "[386DX ISA] MR 386DX (Opti495)", "mr_386dx_opti495", L"opti495/mr", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_AT | MACHINE_HDC, 1, 64, 1, 128, m_at_opti495_mr_init, NULL, NULL },
{ "[386DX ISA] AMI 386DX (Opti495)", "ami_386dx_opti495", L"opti495/ami", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_AT | MACHINE_HDC, 1, 32, 1, 128, m_at_opti495_ami_init, NULL, NULL },
{ "[386DX ISA] Award 386DX (Opti495)", "award_386dx_opti495", L"opti495/award", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_AT | MACHINE_HDC, 1, 32, 1, 128, m_at_opti495_award_init, NULL, NULL },
{ "[386DX ISA] MR 386DX (Opti495)", "mr_386dx_opti495", L"opti495/mr", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_AT | MACHINE_HDC, 1, 32, 1, 128, m_at_opti495_mr_init, NULL, NULL },
{ "[386DX ISA] Amstrad MegaPC 386DX", "amstrad_megapc_dx", L"amstrad/megapc", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_AT | MACHINE_PS2 | MACHINE_HDC | MACHINE_VIDEO, 1, 32, 1, 128, m_at_wd76c10_init, NULL, NULL },
#if defined(DEV_BRANCH) && defined(USE_PORTABLE3)
@@ -156,9 +156,9 @@ const machine_t machines[] = {
#if defined(DEV_BRANCH) && defined(USE_SIS471)
{ "[486 ISA] AMI 486 (SiS471)", "ami_486_sis471", L"sis471/ami", 0, {{"Intel", cpus_i486}, {"AMD", cpus_Am486}, {"Cyrix", cpus_Cx486}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_VLB | MACHINE_AT | MACHINE_HDC, 1, 128, 1, 128, m_at_sis471_ami_init, NULL, NULL },
#endif
{ "[486 ISA] AMI WinBIOS486 (ALi1429)", "ami_win486_ali1429", L"ali1429/ami_win", 0, {{"Intel", cpus_i486}, {"AMD", cpus_Am486}, {"Cyrix", cpus_Cx486}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_VLB | MACHINE_AT | MACHINE_HDC, 1, 64, 1, 128, m_at_ali1429_init, NULL, NULL },
{ "[486 ISA] Award 486 (Opti495)", "award_486_opti495", L"opti495/award", 0, {{"Intel", cpus_i486}, {"AMD", cpus_Am486}, {"Cyrix", cpus_Cx486}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_VLB | MACHINE_AT | MACHINE_HDC, 1, 64, 1, 128, m_at_opti495_award_init, NULL, NULL },
{ "[486 ISA] MR 486 (Opti495)", "mr_486dx_opti495", L"opti495/mr", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_VLB | MACHINE_AT | MACHINE_HDC, 1, 64, 1, 128, m_at_opti495_mr_init, NULL, NULL },
{ "[486 ISA] AMI WinBIOS486 (ALi1429)", "ami_win486_ali1429", L"ali1429/ami_win", 0, {{"Intel", cpus_i486}, {"AMD", cpus_Am486}, {"Cyrix", cpus_Cx486}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_VLB | MACHINE_AT | MACHINE_HDC, 1, 32, 1, 128, m_at_ali1429_init, NULL, NULL },
{ "[486 ISA] Award 486 (Opti495)", "award_486_opti495", L"opti495/award", 0, {{"Intel", cpus_i486}, {"AMD", cpus_Am486}, {"Cyrix", cpus_Cx486}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_VLB | MACHINE_AT | MACHINE_HDC, 1, 32, 1, 128, m_at_opti495_award_init, NULL, NULL },
{ "[486 ISA] MR 486 (Opti495)", "mr_486dx_opti495", L"opti495/mr", 0, {{"Intel", cpus_i386DX}, {"AMD", cpus_Am386DX}, {"Cyrix", cpus_486DLC}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_VLB | MACHINE_AT | MACHINE_HDC, 1, 32, 1, 128, m_at_opti495_mr_init, NULL, NULL },
{ "[486 ISA] DTK PKM-0038S E-2", "dtk_486", L"dtk/486", 0, {{"Intel", cpus_i486}, {"AMD", cpus_Am486}, {"Cyrix", cpus_Cx486}, {"", NULL}, {"", NULL}}, 0, MACHINE_ISA | MACHINE_VLB | MACHINE_AT | MACHINE_HDC, 1, 128, 1, 128, m_at_dtk486_init, NULL, NULL },