From 18be0dfc0b9b0dfdcbaa8942a047881677ed42f7 Mon Sep 17 00:00:00 2001 From: drmortalwombat <90205530+drmortalwombat@users.noreply.github.com> Date: Sat, 29 Jan 2022 21:55:52 +0100 Subject: [PATCH] Optimize dynamic code generation --- include/crt.c | 11 + include/fixmath.c | 358 +++++++++++++++++++++++++++++++ include/fixmath.h | 30 +++ include/gfx/bitmap.c | 92 ++++---- include/gfx/vector3d.c | 2 +- oscar64/NativeCodeGenerator.cpp | 14 ++ oscar64/oscar64.cpp | 2 +- oscar64/oscar64.rc | 8 +- oscar64setup/oscar64setup.vdproj | 84 +++++++- samples/hires/cube3d.c | 178 +++++++++++++-- 10 files changed, 705 insertions(+), 74 deletions(-) create mode 100644 include/fixmath.c create mode 100644 include/fixmath.h diff --git a/include/crt.c b/include/crt.c index d5d2c41..3b84446 100644 --- a/include/crt.c +++ b/include/crt.c @@ -401,6 +401,16 @@ LS1: rol accu rol accu + 3 rol tmp + 4 rol tmp + 5 + bcc LS1a + + lda tmp + 4 + sbc tmp + tax + lda tmp + 5 + sbc tmp + 1 + sec + bcs LS1b +LS1a: sec lda tmp + 4 sbc tmp @@ -408,6 +418,7 @@ LS1: rol accu lda tmp + 5 sbc tmp + 1 bcc WS1 +LS1b: stx tmp + 4 sta tmp + 5 WS1: dey diff --git a/include/fixmath.c b/include/fixmath.c new file mode 100644 index 0000000..651e197 --- /dev/null +++ b/include/fixmath.c @@ -0,0 +1,358 @@ +#include "fixmath.h" + +unsigned long lmul16u(unsigned x, unsigned y) +{ + __asm + { + lda #0 + sta accu + 2 + sta accu + 3 + + ldx #16 +L1: lsr x + 1 + ror x + bcc W1 + clc + lda accu + 2 + adc y + sta accu + 2 + lda accu + 3 + adc y + 1 + sta accu + 3 +W1: + ror accu + 3 + ror accu + 2 + ror accu + 1 + ror accu + dex + bne L1 + } +} + +long lmul16s(int x, int y) +{ + __asm + { + bit y + 1 + bpl W0 + + sec + lda #0 + sbc y + sta y + lda #0 + sbc y + 1 + sta y + 1 + + sec + lda #0 + sbc x + sta x + lda #0 + sbc x + 1 + sta x + 1 +W0: + ldx #15 + lda #0 + sta accu + 2 + +L1: lsr x + 1 + ror x + bcc W1 + tay + clc + lda accu + 2 + adc y + sta accu + 2 + tya + adc y + 1 +W1: + ror + ror accu + 2 + ror accu + 1 + ror accu + dex + bne L1 + + lsr x + bcc W2 + + tay + sec + lda accu + 2 + sbc y + sta accu + 2 + tya + sbc y + 1 + + sec +W2: + ror + ror accu + 2 + ror accu + 1 + ror accu + sta accu + 3 + + } +} + +inline int lmul12f4s(int x, int y) +{ + return (int)(lmul16s(x, y) >> 4); +} + +inline int lmul8f8s(int x, int y) +{ + return (int)(lmul16s(x, y) >> 8); +} + +int lmul4f12s(int x, int y) +{ + __asm + { + bit y + 1 + bpl W0 + + sec + lda #0 + sbc y + sta y + lda #0 + sbc y + 1 + sta y + 1 + + sec + lda #0 + sbc x + sta x + lda #0 + sbc x + 1 + sta x + 1 +W0: + ldx #15 + lda #0 + sta accu + 1 + +L1: lsr x + 1 + ror x + bcc W1 + tay + clc + lda accu + 1 + adc y + sta accu + 1 + tya + adc y + 1 +W1: + ror + ror accu + 1 + ror accu + dex + bne L1 + + lsr x + bcc W2 + + tay + sec + lda accu + 1 + sbc y + sta accu + 1 + tya + sbc y + 1 + + sec +W2: + ror + ror accu + 1 + ror accu + + lsr + ror accu + 1 + ror accu + + lsr + ror accu + 1 + ror accu + + lsr + ror accu + 1 + ror accu + + lsr + ror accu + 1 + ror accu + } +} + +unsigned ldiv16u(unsigned long x, unsigned y) +{ + __asm + { + lda #0 + sta accu + sta accu + 1 + + ldx #17 + L1: + sec + lda x + 2 + sbc y + tay + lda x + 3 + sbc y + 1 + bcc W1 + sta x + 3 + sty x + 2 + W1: + rol accu + rol accu + 1 + + asl x + rol x + 1 + rol x + 2 + rol x + 3 + + dex + beq E1 + bcc L1 + + lda x + 2 + sbc y + sta x + 2 + lda x + 3 + sbc y + 1 + sta x + 3 + sec + bcs W1 + E1: + } +} + +int ldiv16s(long x, int y) +{ + if (x < 0) + { + if (y < 0) + return ldiv16u(-x, - y); + else + return -ldiv16u(-x, y); + } + else if (y < 0) + return -ldiv16u(x, -y); + else + return ldiv16u(x, y); +} + +inline int ldiv12f4s(int x, int y) +{ + return (int)(ldiv16s((long)x << 4, y)); +} + +inline int ldiv8f8s(int x, int y) +{ + return (int)(ldiv16s((long)x << 8, y)); +} + +inline int ldiv4f12s(int x, int y) +{ + return (int)(ldiv16s((long)x << 12, y)); +} + +unsigned lmuldiv16u(unsigned a, unsigned b, unsigned c) +{ + __asm + { + lda #0 + sta __tmp + 0 + sta __tmp + 1 + sta __tmp + 2 + sta __tmp + 3 + + ldx #16 + L1: lsr a + 1 + ror a + bcc W1 + clc + lda __tmp + 2 + adc b + sta __tmp + 2 + lda __tmp + 3 + adc b + 1 + sta __tmp + 3 + W1: + ror __tmp + 3 + ror __tmp + 2 + ror __tmp + 1 + ror __tmp + dex + bne L1 + + lda #0 + sta accu + sta accu + 1 + + ldx #17 + L2: + sec + lda __tmp + 2 + sbc c + tay + lda __tmp + 3 + sbc c + 1 + bcc W2 + sta __tmp + 3 + sty __tmp + 2 + W2: + rol accu + rol accu + 1 + + asl __tmp + rol __tmp + 1 + rol __tmp + 2 + rol __tmp + 3 + + dex + beq E2 + bcc L2 + + lda __tmp + 2 + sbc c + sta __tmp + 2 + lda __tmp + 3 + sbc c + 1 + sta __tmp + 3 + sec + bcs W2 + E2: + + } + +} + +int lmuldiv16s(int a, int b, int c) +{ + bool sign = false; + if (a < 0) + { + a = -a; + sign = !sign; + } + if (b < 0) + { + b = -b; + sign = !sign; + } + if (c < 0) + { + c = -c; + sign = !sign; + } + + long v = lmuldiv16u(a, b, c); + + if (sign) + return -v; + else + return v; +} diff --git a/include/fixmath.h b/include/fixmath.h new file mode 100644 index 0000000..ba78710 --- /dev/null +++ b/include/fixmath.h @@ -0,0 +1,30 @@ +#ifndef FIXMATH_H +#define FIXMATH_H + +__native unsigned long lmul16u(unsigned x, unsigned y); + +__native long lmul16s(int x, int y) + +inline int lmul12f4s(int x, int y); + +inline int lmul8f8s(int x, int y); + +__native int lmul4f12s(int x, int y) + +__native unsigned ldiv16u(unsigned long x, unsigned y) + +__native int ldiv16s(long x, int y) + +inline int ldiv12f4s(int x, int y) + +inline int ldiv8f8s(int x, int y) + +inline int ldiv4f12s(int x, int y) + +__native unsigned lmuldiv16u(unsigned a, unsigned b, unsigned c) + +__native int lmuldiv16s(int a, int b, int c) + +#pragma compile("fixmath.c") + +#endif diff --git a/include/gfx/bitmap.c b/include/gfx/bitmap.c index 0c854bc..c135e21 100644 --- a/include/gfx/bitmap.c +++ b/include/gfx/bitmap.c @@ -3,6 +3,7 @@ #include #include #include +#include void bm_init(Bitmap * bm, char * data, char cw, char ch) { @@ -480,9 +481,10 @@ void bm_polygon_nc_fill(Bitmap * bm, ClipRect * clip, int * px, int * py, char n #define REG_D0 0x0a #define REG_D1 0x0b -static void buildline(char ly, char lx, int dx, int dy, int stride, bool left, bool up, char pattern, LineOp op) +static inline void buildline(char ly, char lx, int dx, int dy, int stride, bool left, bool up, char pattern, LineOp op) { char ip = 0; + bool delta16 = ((dx | dy) & 0xff80) != 0; // ylow ip += asm_im(BLIT_CODE + ip, ASM_LDY, ly); @@ -537,8 +539,8 @@ static void buildline(char ly, char lx, int dx, int dy, int stride, bool left, b } // m >= 0 - ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP + 1); - ip += asm_rl(BLIT_CODE + ip, ASM_BMI, 5 + 15 + 13); + ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP + delta16); + ip += asm_rl(BLIT_CODE + ip, ASM_BMI, delta16 ? 5 + 15 + 13 + 2 : 5 + 15 + 7 + 2); ip += asm_np(BLIT_CODE + ip, up ? ASM_DEY : ASM_INY); ip += asm_im(BLIT_CODE + ip, ASM_CPY, up ? 0xff : 0x08); @@ -557,13 +559,16 @@ static void buildline(char ly, char lx, int dx, int dy, int stride, bool left, b ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP); ip += asm_im(BLIT_CODE + ip, ASM_SBC, dx & 0xff); ip += asm_zp(BLIT_CODE + ip, ASM_STA, REG_DP); - ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP + 1); - ip += asm_im(BLIT_CODE + ip, ASM_SBC, dx >> 8); - ip += asm_zp(BLIT_CODE + ip, ASM_STA, REG_DP + 1); + + if (delta16) + { + ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP + 1); + ip += asm_im(BLIT_CODE + ip, ASM_SBC, dx >> 8); + ip += asm_zp(BLIT_CODE + ip, ASM_STA, REG_DP + 1); + } // m < 0 - ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP + 1); - ip += asm_rl(BLIT_CODE + ip, ASM_BPL, 4 + 15 + 13); + ip += asm_rl(BLIT_CODE + ip, ASM_BPL, delta16 ? 4 + 15 + 13 : 4 + 15 + 7); ip += asm_zp(BLIT_CODE + ip, left ? ASM_ASL : ASM_LSR, REG_D0); ip += asm_rl(BLIT_CODE + ip, ASM_BCC, 15); @@ -581,9 +586,12 @@ static void buildline(char ly, char lx, int dx, int dy, int stride, bool left, b ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP); ip += asm_im(BLIT_CODE + ip, ASM_ADC, dy & 0xff); ip += asm_zp(BLIT_CODE + ip, ASM_STA, REG_DP); - ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP + 1); - ip += asm_im(BLIT_CODE + ip, ASM_ADC, dy >> 8); - ip += asm_zp(BLIT_CODE + ip, ASM_STA, REG_DP + 1); + if (delta16) + { + ip += asm_zp(BLIT_CODE + ip, ASM_LDA, REG_DP + 1); + ip += asm_im(BLIT_CODE + ip, ASM_ADC, dy >> 8); + ip += asm_zp(BLIT_CODE + ip, ASM_STA, REG_DP + 1); + } // l -- ip += asm_np(BLIT_CODE + ip, ASM_DEX); @@ -639,126 +647,120 @@ void bmu_line(Bitmap * bm, int x0, int y0, int x1, int y1, char pattern, LineOp op = LINOP_OR; int dx = x1 - x0, dy = y1 - y0; - byte quad = 0; + bool left = false; + bool up = false; + if (dx < 0) { - quad = 1; + left = true; dx = -dx; } if (dy < 0) { - quad |= 2; + up = true; dy = -dy; } int l; - if (dx > dy) + if ((unsigned)dx > (unsigned)dy) l = dx; else l = dy; int m = dy - dx; - dx *= 2; - dy *= 2; + if (m & 1) + { + dx *= 2; + dy *= 2; + } + else + { + m >>= 1; + } char * dp = bm->data + bm->cwidth * (y0 & ~7) + (x0 & ~7); char bit = 0x80 >> (x0 & 7); char ry = y0 & 7; int stride = 8 * bm->cwidth; - buildline(ry, (l + 1) & 0xff, dx, dy, (quad & 2) ? -stride : stride, quad & 1, quad & 2, pattern, op); + buildline(ry, (l + 1) & 0xff, dx, dy, up ? -stride : stride, left, up, pattern, op); callline(dp, bit, m, l >> 8, pattern); } -static int muldiv(int x, int mul, int div) -{ - return (int)((long)x * mul / div); -} - void bm_line(Bitmap * bm, ClipRect * clip, int x0, int y0, int x1, int y1, char pattern, LineOp op) { int dx = x1 - x0, dy = y1 - y0; - if (x0 < x1) + if (dx > 0) { if (x1 < clip->left || x0 >= clip->right) return; if (x0 < clip->left) { - y0 += muldiv(clip->left - x0, dy, dx); + y0 += lmuldiv16s(clip->left - x0, dy, dx); x0 = clip->left; } if (x1 >= clip->right) { - y1 -= muldiv(x1 + 1 - clip->right, dy, dx); + y1 -= lmuldiv16s(x1 + 1 - clip->right, dy, dx); x1 = clip->right - 1; } } - else if (x1 < x0) + else { if (x0 < clip->left || x1 >= clip->right) return; if (x1 < clip->left) { - y1 += muldiv(clip->left - x1, dy, dx); + y1 += lmuldiv16s(clip->left - x1, dy, dx); x1 = clip->left; } if (x0 >= clip->right) { - y0 -= muldiv(x0 + 1- clip->right, dy, dx); + y0 -= lmuldiv16s(x0 + 1- clip->right, dy, dx); x0 = clip->right - 1; } } - else - { - if (x0 < clip->left || x0 >= clip->right) - return; - } - if (y0 < y1) + if (dy > 0) { if (y1 < clip->top || y0 >= clip->bottom) return; if (y0 < clip->top) { - x0 += muldiv(clip->top - y0, dx, dy); + x0 += lmuldiv16s(clip->top - y0, dx, dy); y0 = clip->top; } if (y1 >= clip->bottom) { - x1 -= muldiv(y1 + 1 - clip->bottom, dx, dy); + x1 -= lmuldiv16s(y1 + 1 - clip->bottom, dx, dy); y1 = clip->bottom - 1; } } - else if (y1 < y0) + else { if (y0 < clip->top || y1 >= clip->bottom) return; if (y1 < clip->top) { - x1 += muldiv(clip->top - y1, dx, dy); + x1 += lmuldiv16s(clip->top - y1, dx, dy); y1 = clip->top; } if (y0 >= clip->bottom) { - x0 -= muldiv(y0 + 1 - clip->bottom, dx, dy); + x0 -= lmuldiv16s(y0 + 1 - clip->bottom, dx, dy); y0 = clip->bottom - 1; } } - else - { - if (y0 < clip->top || y0 >= clip->bottom) - return; - } bmu_line(bm, x0, y0, x1, y1, pattern, op); } diff --git a/include/gfx/vector3d.c b/include/gfx/vector3d.c index f3430c7..5ba7b76 100644 --- a/include/gfx/vector3d.c +++ b/include/gfx/vector3d.c @@ -416,7 +416,7 @@ void mat3_mmul(Matrix3 * md, const Matrix3 * ms) { for(char i=0; i<3; i++) { - float j = 3 * i; + char j = 3 * i; float m0 = md->m[i + 0] * ms->m[0] + md->m[i + 3] * ms->m[1] + md->m[i + 6] * ms->m[2]; float m3 = md->m[i + 0] * ms->m[3] + md->m[i + 3] * ms->m[4] + md->m[i + 6] * ms->m[5]; diff --git a/oscar64/NativeCodeGenerator.cpp b/oscar64/NativeCodeGenerator.cpp index 4e17919..e990cc1 100644 --- a/oscar64/NativeCodeGenerator.cpp +++ b/oscar64/NativeCodeGenerator.cpp @@ -14287,6 +14287,20 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(int pass) progress = true; } #endif +#if 1 + else if ( + mIns[i + 0].mType == ASMIT_LDA && mIns[i + 0].mMode == ASMIM_IMMEDIATE && mIns[i + 0].mAddress == 0x00 && + mIns[i + 1].mType == ASMIT_ADC && mIns[i + 1].mMode == ASMIM_IMMEDIATE && mIns[i + 1].mAddress == 0xff && + mIns[i + 2].mType == ASMIT_AND && mIns[i + 2].mMode == ASMIM_IMMEDIATE && mIns[i + 2].mAddress == 0x01 && + mIns[i + 3].mType == ASMIT_EOR && mIns[i + 3].mMode == ASMIM_IMMEDIATE && mIns[i + 3].mAddress == 0x01) + { + mIns[i + 1].mAddress = 0x00; + mIns[i + 2].mType = ASMIT_NOP; mIns[i + 2].mMode = ASMIM_IMPLIED; + mIns[i + 3].mType = ASMIT_NOP; mIns[i + 3].mMode = ASMIM_IMPLIED; + + progress = true; + } +#endif else if ( mIns[i + 0].mType == ASMIT_LDA && mIns[i + 3].mType == ASMIT_STA && mIns[i + 0].SameEffectiveAddress(mIns[i + 3]) && diff --git a/oscar64/oscar64.cpp b/oscar64/oscar64.cpp index 97aa698..3bab0ca 100644 --- a/oscar64/oscar64.cpp +++ b/oscar64/oscar64.cpp @@ -73,7 +73,7 @@ int main(int argc, const char** argv) #else strcpy(strProductName, "oscar64"); - strcpy(strProductVersion, "1.3.73"); + strcpy(strProductVersion, "1.3.74"); #ifdef __APPLE__ uint32_t length = sizeof(basePath); diff --git a/oscar64/oscar64.rc b/oscar64/oscar64.rc index 1b349ed..5a95c7f 100644 --- a/oscar64/oscar64.rc +++ b/oscar64/oscar64.rc @@ -25,8 +25,8 @@ LANGUAGE LANG_ENGLISH, SUBLANG_NEUTRAL // VS_VERSION_INFO VERSIONINFO - FILEVERSION 1,3,73,0 - PRODUCTVERSION 1,3,73,0 + FILEVERSION 1,3,74,0 + PRODUCTVERSION 1,3,74,0 FILEFLAGSMASK 0x3fL #ifdef _DEBUG FILEFLAGS 0x1L @@ -43,12 +43,12 @@ BEGIN BEGIN VALUE "CompanyName", "oscar64" VALUE "FileDescription", "oscar64 compiler" - VALUE "FileVersion", "1.3.73.0" + VALUE "FileVersion", "1.3.74.0" VALUE "InternalName", "oscar64.exe" VALUE "LegalCopyright", "Copyright (C) 2021" VALUE "OriginalFilename", "oscar64.exe" VALUE "ProductName", "oscar64" - VALUE "ProductVersion", "1.3.73.0" + VALUE "ProductVersion", "1.3.74.0" END END BLOCK "VarFileInfo" diff --git a/oscar64setup/oscar64setup.vdproj b/oscar64setup/oscar64setup.vdproj index c51e43b..350b56c 100644 --- a/oscar64setup/oscar64setup.vdproj +++ b/oscar64setup/oscar64setup.vdproj @@ -70,6 +70,12 @@ } "Entry" { + "MsmKey" = "8:_12C998C755E643038CDF5D9F56983ECA" + "OwnerKey" = "8:_UNDEFINED" + "MsmSig" = "8:_UNDEFINED" + } + "Entry" + { "MsmKey" = "8:_1393003825B9451084DB314DD4267AD5" "OwnerKey" = "8:_UNDEFINED" "MsmSig" = "8:_UNDEFINED" @@ -274,6 +280,12 @@ } "Entry" { + "MsmKey" = "8:_67F949223D154D92A9EC79A2A9CD1C97" + "OwnerKey" = "8:_UNDEFINED" + "MsmSig" = "8:_UNDEFINED" + } + "Entry" + { "MsmKey" = "8:_683E44581EBB4154841523B526E1B4B4" "OwnerKey" = "8:_UNDEFINED" "MsmSig" = "8:_UNDEFINED" @@ -496,6 +508,12 @@ } "Entry" { + "MsmKey" = "8:_BA92710604A2499F8577F52758F3F529" + "OwnerKey" = "8:_UNDEFINED" + "MsmSig" = "8:_UNDEFINED" + } + "Entry" + { "MsmKey" = "8:_BAE9C5C261D54D06B5CBE68CDFA3809F" "OwnerKey" = "8:_UNDEFINED" "MsmSig" = "8:_UNDEFINED" @@ -989,6 +1007,26 @@ "IsDependency" = "11:FALSE" "IsolateTo" = "8:" } + "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_12C998C755E643038CDF5D9F56983ECA" + { + "SourcePath" = "8:..\\include\\fixmath.h" + "TargetName" = "8:fixmath.h" + "Tag" = "8:" + "Folder" = "8:_7C0D28C244F14A21B5F72213BBE59B6F" + "Condition" = "8:" + "Transitive" = "11:FALSE" + "Vital" = "11:TRUE" + "ReadOnly" = "11:FALSE" + "Hidden" = "11:FALSE" + "System" = "11:FALSE" + "Permanent" = "11:FALSE" + "SharedLegacy" = "11:FALSE" + "PackageAs" = "3:1" + "Register" = "3:1" + "Exclude" = "11:FALSE" + "IsDependency" = "11:FALSE" + "IsolateTo" = "8:" + } "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_1393003825B9451084DB314DD4267AD5" { "SourcePath" = "8:..\\samples\\memmap\\allmem.c" @@ -1669,6 +1707,26 @@ "IsDependency" = "11:FALSE" "IsolateTo" = "8:" } + "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_67F949223D154D92A9EC79A2A9CD1C97" + { + "SourcePath" = "8:..\\samples\\hires\\cube3d.c" + "TargetName" = "8:cube3d.c" + "Tag" = "8:" + "Folder" = "8:_82FDD682B0334DE1B89A843D32862B85" + "Condition" = "8:" + "Transitive" = "11:FALSE" + "Vital" = "11:TRUE" + "ReadOnly" = "11:FALSE" + "Hidden" = "11:FALSE" + "System" = "11:FALSE" + "Permanent" = "11:FALSE" + "SharedLegacy" = "11:FALSE" + "PackageAs" = "3:1" + "Register" = "3:1" + "Exclude" = "11:FALSE" + "IsDependency" = "11:FALSE" + "IsolateTo" = "8:" + } "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_683E44581EBB4154841523B526E1B4B4" { "SourcePath" = "8:..\\samples\\memmap\\make.bat" @@ -2409,6 +2467,26 @@ "IsDependency" = "11:FALSE" "IsolateTo" = "8:" } + "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_BA92710604A2499F8577F52758F3F529" + { + "SourcePath" = "8:..\\include\\fixmath.c" + "TargetName" = "8:fixmath.c" + "Tag" = "8:" + "Folder" = "8:_7C0D28C244F14A21B5F72213BBE59B6F" + "Condition" = "8:" + "Transitive" = "11:FALSE" + "Vital" = "11:TRUE" + "ReadOnly" = "11:FALSE" + "Hidden" = "11:FALSE" + "System" = "11:FALSE" + "Permanent" = "11:FALSE" + "SharedLegacy" = "11:FALSE" + "PackageAs" = "3:1" + "Register" = "3:1" + "Exclude" = "11:FALSE" + "IsDependency" = "11:FALSE" + "IsolateTo" = "8:" + } "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_BAE9C5C261D54D06B5CBE68CDFA3809F" { "SourcePath" = "8:..\\include\\setjmp.h" @@ -3414,15 +3492,15 @@ { "Name" = "8:Microsoft Visual Studio" "ProductName" = "8:oscar64" - "ProductCode" = "8:{A53359B5-4B83-418F-BE3F-60133D152224}" - "PackageCode" = "8:{5B0C1429-92B6-4506-ABF5-36A623D4C056}" + "ProductCode" = "8:{109FC925-4A6D-4868-A60D-42BF3DFE541B}" + "PackageCode" = "8:{C6215A39-7DD0-4667-93FB-46373135B9C8}" "UpgradeCode" = "8:{9AB61EFF-ACAC-4079-9950-8D96615CD4EF}" "AspNetVersion" = "8:2.0.50727.0" "RestartWWWService" = "11:FALSE" "RemovePreviousVersions" = "11:TRUE" "DetectNewerInstalledVersion" = "11:TRUE" "InstallAllUsers" = "11:FALSE" - "ProductVersion" = "8:1.3.73" + "ProductVersion" = "8:1.3.74" "Manufacturer" = "8:oscar64" "ARPHELPTELEPHONE" = "8:" "ARPHELPLINK" = "8:" diff --git a/samples/hires/cube3d.c b/samples/hires/cube3d.c index ff04fc6..212cd2f 100644 --- a/samples/hires/cube3d.c +++ b/samples/hires/cube3d.c @@ -6,6 +6,7 @@ #include #include #include +#include char * const Color = (char *)0xd000; char * const Hires = (char *)0xe000; @@ -33,13 +34,11 @@ void done(void) { mmap_set(MMAP_ROM); - getch(); +// getch(); vic_setmode(VICM_TEXT, (char *)0x0400, (char *)0x1000); } -Matrix4 wmat, pmat, tmat, rmat; -Vector3 corners[8]; ClipRect cr = {0, 0, 320, 200}; @@ -48,6 +47,16 @@ struct Point int x, y; }; +struct FVector3 +{ + int v[3]; +}; + +struct FMatrix3 +{ + int m[9]; +}; + Point tcorners[8], pcorners[8]; void drawCube(void) @@ -55,11 +64,11 @@ void drawCube(void) for(char i=0; i<8; i++) { if (!(i & 1)) - bm_line(&Screen, &cr, tcorners[i].x, tcorners[i].y, tcorners[i | 1].x, tcorners[i | 1].y, 0xff, LINOP_XOR); + bm_line(&Screen, &cr, tcorners[i].x, tcorners[i].y, tcorners[i | 1].x, tcorners[i | 1].y, 0xff, LINOP_OR); if (!(i & 2)) - bm_line(&Screen, &cr, tcorners[i].x, tcorners[i].y, tcorners[i | 2].x, tcorners[i | 2].y, 0xff, LINOP_XOR); + bm_line(&Screen, &cr, tcorners[i].x, tcorners[i].y, tcorners[i | 2].x, tcorners[i | 2].y, 0xff, LINOP_OR); if (!(i & 4)) - bm_line(&Screen, &cr, tcorners[i].x, tcorners[i].y, tcorners[i | 4].x, tcorners[i | 4].y, 0xff, LINOP_XOR); + bm_line(&Screen, &cr, tcorners[i].x, tcorners[i].y, tcorners[i | 4].x, tcorners[i | 4].y, 0xff, LINOP_OR); pcorners[i] = tcorners[i]; } } @@ -69,14 +78,142 @@ void hideCube(void) for(char i=0; i<8; i++) { if (!(i & 1)) - bm_line(&Screen, &cr, pcorners[i].x, pcorners[i].y, pcorners[i | 1].x, pcorners[i | 1].y, 0xff, LINOP_XOR); + bm_line(&Screen, &cr, pcorners[i].x, pcorners[i].y, pcorners[i | 1].x, pcorners[i | 1].y, 0xff, LINOP_AND); if (!(i & 2)) - bm_line(&Screen, &cr, pcorners[i].x, pcorners[i].y, pcorners[i | 2].x, pcorners[i | 2].y, 0xff, LINOP_XOR); + bm_line(&Screen, &cr, pcorners[i].x, pcorners[i].y, pcorners[i | 2].x, pcorners[i | 2].y, 0xff, LINOP_AND); if (!(i & 4)) - bm_line(&Screen, &cr, pcorners[i].x, pcorners[i].y, pcorners[i | 4].x, pcorners[i | 4].y, 0xff, LINOP_XOR); + bm_line(&Screen, &cr, pcorners[i].x, pcorners[i].y, pcorners[i | 4].x, pcorners[i | 4].y, 0xff, LINOP_AND); } } +#if 1 + +FVector3 corners[8]; + +static const int FMOne = 1 << 12; + +void fmat3_ident(FMatrix3 * m) +{ + m->m[0] = FMOne; + m->m[1] = 0; + m->m[2] = 0; + + m->m[3] = 0; + m->m[4] = FMOne; + m->m[5] = 0; + + m->m[6] = 0; + m->m[7] = 0; + m->m[8] = FMOne; +} + +void fmat3_mmul(FMatrix3 * md, const FMatrix3 * ms) +{ + for(char i=0; i<3; i++) + { + char j = 3 * i; + + int m0 = lmul4f12s(md->m[i + 0], ms->m[0]) + lmul4f12s(md->m[i + 3], ms->m[1]) + lmul4f12s(md->m[i + 6], ms->m[2]); + int m3 = lmul4f12s(md->m[i + 0], ms->m[3]) + lmul4f12s(md->m[i + 3], ms->m[4]) + lmul4f12s(md->m[i + 6], ms->m[5]); + int m6 = lmul4f12s(md->m[i + 0], ms->m[6]) + lmul4f12s(md->m[i + 3], ms->m[7]) + lmul4f12s(md->m[i + 6], ms->m[8]); + + md->m[i + 0] = m0; md->m[i + 3] = m3; md->m[i + 6] = m6; + } +} + +void fmat3_rmmul(FMatrix3 * md, const FMatrix3 * ms) +{ + for(char i=0; i<9; i+=3) + { + int m0 = lmul4f12s(md->m[i + 0], ms->m[0]) + lmul4f12s(md->m[i + 1], ms->m[3]) + lmul4f12s(md->m[i + 2], ms->m[6]); + int m1 = lmul4f12s(md->m[i + 0], ms->m[1]) + lmul4f12s(md->m[i + 1], ms->m[4]) + lmul4f12s(md->m[i + 2], ms->m[7]); + int m2 = lmul4f12s(md->m[i + 0], ms->m[2]) + lmul4f12s(md->m[i + 1], ms->m[5]) + lmul4f12s(md->m[i + 2], ms->m[8]); + + md->m[i + 0] = m0; md->m[i + 1] = m1; md->m[i + 2] = m2; + } +} + +void fmat3_set_rotate_x(FMatrix3 * m, float a) +{ + int c = (int)(FMOne * cos(a)); + int s = (int)(FMOne * sin(a)); + m->m[0] = FMOne; m->m[3] = 0; m->m[6] = 0; + m->m[1] = 0; m->m[4] = c; m->m[7] = s; + m->m[2] = 0; m->m[5] =-s; m->m[8] = c; +} + +void fmat3_set_rotate_y(FMatrix3 * m, float a) +{ + int c = (int)(FMOne * cos(a)); + int s = (int)(FMOne * sin(a)); + m->m[0] = c; m->m[3] = 0; m->m[6] = s; + m->m[1] = 0; m->m[4] = FMOne; m->m[7] = 0; + m->m[2] =-s; m->m[5] = 0; m->m[8] = c; +} + + +void fmat3_set_rotate_z(FMatrix3 * m, float a) +{ + int c = (int)(FMOne * cos(a)); + int s = (int)(FMOne * sin(a)); + m->m[0] = c; m->m[3] =-s; m->m[6] = 0; + m->m[1] = s; m->m[4] = c; m->m[7] = 0; + m->m[2] = 0; m->m[5] = 0; m->m[8] = FMOne; +} + +void fvec3_mmul(FVector3 * vd, const FMatrix3 * m, const FVector3 * vs) +{ + FVector3 vt; + for(char i=0; i<3; i++) + vt.v[i] = lmul4f12s(m->m[i], vs->v[0]) + lmul4f12s(m->m[3 + i], vs->v[1]) + lmul4f12s(m->m[6 + i], vs->v[2]); + *vd = vt; +} + + +FMatrix3 rmat, tmat; + +int main(void) +{ + init(); + + for(char i=0; i<8; i++) + { + corners[i].v[0] = (i & 1) ? -FMOne : FMOne; + corners[i].v[1] = (i & 2) ? -FMOne : FMOne; + corners[i].v[2] = (i & 4) ? -FMOne : FMOne; + } + + for(int k=0; k<100; k++) + { + fmat3_set_rotate_x(&rmat, 0.1 * k); + fmat3_set_rotate_y(&tmat, 0.06 * k); + fmat3_mmul(&rmat, &tmat); + + for(char i=0; i<8; i++) + { + FVector3 vd; + + fvec3_mmul(&vd, &rmat, corners + i); + + tcorners[i].x = lmuldiv16s(vd.v[0], 140, vd.v[2] + 4 * FMOne) + 160; + tcorners[i].y = lmuldiv16s(vd.v[1], 140, vd.v[2] + 4 * FMOne) + 100; + } + + hideCube(); + drawCube(); + + } + + done(); + + return 0; +} + +#else + +Matrix4 wmat, pmat, tmat, rmat; +Vector3 corners[8]; + int main(void) { init(); @@ -86,6 +223,14 @@ int main(void) mat4_scale(&wmat, 1); + for(char i=0; i<8; i++) + { + vec3_set(corners + i, + (i & 1) ? -1.0 : 1.0, + (i & 2) ? -1.0 : 1.0, + (i & 4) ? -1.0 : 1.0); + } + for(int k=0; k<100; k++) { mat4_set_rotate_x(&rmat, 0.1 * k); @@ -93,20 +238,11 @@ int main(void) mat4_rmmul(&rmat, &tmat); mat4_rmmul(&rmat, &wmat); - rmat.m[14] += 5.0; + rmat.m[14] += 4.0; tmat = pmat; mat4_mmul(&tmat, &rmat); - for(char i=0; i<8; i++) - { - vec3_set(corners + i, - (i & 1) ? -1.0 : 1.0, - (i & 2) ? -1.0 : 1.0, - (i & 4) ? -1.0 : 1.0); - } - - for(char i=0; i<8; i++) { Vector3 vd; @@ -122,4 +258,6 @@ int main(void) done(); return 0; -} \ No newline at end of file +} + +#endif \ No newline at end of file