diff --git a/part12-wgt/Makefile b/part12-wgt/Makefile index 251e5f7..6633d38 100644 --- a/part12-wgt/Makefile +++ b/part12-wgt/Makefile @@ -17,11 +17,14 @@ bin/wgt1blk.o: bin/wgt1.blk bin/wgt2blk.o: bin/wgt2.blk $(LLVMPATH)/llvm-objcopy -I binary -O elf64-littleaarch64 -B aarch64 $< $@ +bin/lettersspr.o: bin/letters.spr + $(LLVMPATH)/llvm-objcopy -I binary -O elf64-littleaarch64 -B aarch64 $< $@ + %.o: %.c $(LLVMPATH)/clang --target=aarch64-elf $(CLANGFLAGS) -c $< -o $@ -kernel8.img: boot/boot.o $(OFILES) bin/wgt1pal.o bin/wgt1blk.o bin/wgt2blk.o - $(LLVMPATH)/ld.lld -m aarch64elf -nostdlib boot/boot.o $(OFILES) bin/wgt1pal.o bin/wgt1blk.o bin/wgt2blk.o -T boot/link.ld -o kernel8.elf +kernel8.img: boot/boot.o $(OFILES) bin/wgt1pal.o bin/wgt1blk.o bin/wgt2blk.o bin/lettersspr.o + $(LLVMPATH)/ld.lld -m aarch64elf -nostdlib boot/boot.o $(OFILES) bin/wgt1pal.o bin/wgt1blk.o bin/wgt2blk.o bin/lettersspr.o -T boot/link.ld -o kernel8.elf $(LLVMPATH)/llvm-objcopy -O binary kernel8.elf kernel8.img clean: diff --git a/part12-wgt/bin/letters.spr b/part12-wgt/bin/letters.spr new file mode 100644 index 0000000..19d8402 Binary files /dev/null and b/part12-wgt/bin/letters.spr differ diff --git a/part12-wgt/examples/wgt29.c b/part12-wgt/examples/wgt29.c new file mode 100644 index 0000000..8664f11 --- /dev/null +++ b/part12-wgt/examples/wgt29.c @@ -0,0 +1,110 @@ +#include "wgt.h" +#include "include/mem.h" + +// ######## REQUIRED FUNCTIONS ######## + +unsigned long state0 = 1000; +unsigned long state1 = 2000; + +unsigned long rand(void) +{ + unsigned long s1 = state0; + unsigned long s0 = state1; + + state0 = s0; + s1 ^= s1 << 23; + s1 ^= s1 >> 17; + s1 ^= s0; + s1 ^= s0 >> 26; + state1 = s1; + + return state0 + state1; +} + +void wait_msec(unsigned int n) +{ + register unsigned long f, t, r; + + // Get the current counter frequency + asm volatile ("mrs %0, cntfrq_el0" : "=r"(f)); + // Read the current counter + asm volatile ("mrs %0, cntpct_el0" : "=r"(t)); + // Calculate expire value for counter + t+=((f/1000)*n)/1000; + do{asm volatile ("mrs %0, cntpct_el0" : "=r"(r));}while(r 4, maxsprite contains + the number of the highest sprite in the file. (empty sprites at + the end are not kept in the file. */ + if (a <= 3) + startingsprite = 1; + else + startingsprite = 0; + + memcpy_char(&buf, file, 13); + file += 13; + + if (0 == memcmp (" Sprite File ", &buf[0], 13)) + /* see if it is a sprite file */ + { + for (int k=0;k<256;k++) { + pal[k].r = 4 * *file++; + pal[k].g = 4 * *file++; + pal[k].b = 4 * *file++; + } + wsetpalette (0, 255, pal); + + maxsprite = (short)*file; /* maximum sprites in this file */ + file += 2; + + for (i = start; i <= end; i++) /* make all sprites null + (still need to call wfreesprites) */ + image_array[i] = NULL; + + for (i = startingsprite; i <= maxsprite; i++) /* load them in */ + { + spritemade = (unsigned int)*file; /* flag to see if sprite exists */ + file += 2; + if (spritemade == 1) + { + a = (unsigned int)*file; /* get width and height */ + file += 2; + b = (unsigned int)*file; + file += 2; + + if ((i >= start) && (i <= end)) /* Load this one */ + { + size = a * b; + + image_array[i] = (block)malloc ((size * 4) + 12); + block arr = image_array[i]; + + *arr++ = a; + *arr++ = b; + + for (int k=0;k 0) + { + if (*s1++ != *s2++) + return s1[-1] < s2[-1] ? -1 : 1; + } + + return 0; +} + int abs(int i) { return i < 0 ? -i : i; diff --git a/part12-wgt/wgt.h b/part12-wgt/wgt.h index 3271f7e..a89ba1d 100644 --- a/part12-wgt/wgt.h +++ b/part12-wgt/wgt.h @@ -56,6 +56,8 @@ extern short bx,by,tx,ty; void *memset(void *dest, unsigned int val, unsigned len); void *memcpy(void *dest, const void *src, unsigned len); void *memcpy_xray(void *dest, const void *src, unsigned len); +void *memcpy_char(void *dest, const void *src, unsigned len); +int memcmp(char *str1, char *str2, unsigned count); int abs(int i); int strlen(const char *str); @@ -118,3 +120,6 @@ void wnormscreen (void); void wvertres (short x, short y, short y2, block image); void wwipe (short x, short y, short x2, short y2, block image); void wskew (short x, short y, block image, short degrees); +short wloadsprites (color *pal, unsigned char *file, block *image_array, short start, short end); +void wfreesprites (block *image_array, short start, short end); +void wcopyscreen (short x, short y, short x2, short y2, block source, short destx, short desty, block dest); diff --git a/part12-wgt/wscreen.c b/part12-wgt/wscreen.c index 11faa78..02a3b9f 100644 --- a/part12-wgt/wscreen.c +++ b/part12-wgt/wscreen.c @@ -1,5 +1,7 @@ #include "wgt.h" +#define fastcopy memcpy + void wsetscreen (block image) { if (image == NULL) @@ -31,3 +33,67 @@ void wnormscreen (void) bx = WGT_SYS.xres - 1; by = WGT_SYS.yres - 1; } + +void wcopyscreen (short x, short y, short x2, short y2, block source, short destx, short desty, block dest) +{ + unsigned int swidth, dwidth; + short width, height, display; + short ctr; /* Y line counter */ + + if (source == NULL) + { + source = abuf; /* Set to visual screen */ + swidth = 320; + } + else { + swidth = *source; + source += 2; /* Skip over width and height */ + } + + width = abs (x - x2) + 1; /* Width of each row to copy */ + height = abs (y - y2) + 1; /* Height of area to copy */ + + if (destx + width > bx) + display = bx + 1 - destx; + else display = width; /* Clip width */ + + if (height > (by + 1 - desty)) + height = (by + 1 - desty); + + source += x + (y * swidth); /* Clip height */ + if (desty < ty) + { + source += (ty - desty) * swidth; + height -= ty - desty; + desty = ty; + } /* clip y */ + + if (destx < tx) + { + source += tx - destx; + display -= tx - destx; + destx = tx; + } /* clip x */ + + if (dest == NULL) + { + dest = abuf; /* Set to visual screen */ + dwidth = 320; + } + else + { + dwidth = *dest; + dest += 2; + } + + /* Skip over width & height in image data */ + dest += destx + (desty * dwidth); /* Find row offset in image data */ + + if ((height > 0) && (display > 0)) + for (ctr = y; ctr < y + height; ctr++) + { + fastcopy (dest, source, display); /* Copy DISPLAY bytes to dest */ + source += swidth; /* Advance one row */ + dest += dwidth; + } +}