Antoine Vignau fae5db3afd scsi-2 powa!
2024-08-15 21:27:35 +02:00

1 line
14 KiB
C

#include <gsos.h>
#include <memory.h>
#include <malloc.h>
#include <string.h>
#include <quickdraw.h>
#include <qdaux.h>
#include <misctool.h>
typedef struct {
long blkSize;
char identLen;
char ident[4];
int mscb;
int pixPerLine;
int palletteCount;
int pallette[16];
int scanLines;
} infoBlockHdr;
typedef struct {
int numBytes;
int modeWord;
} dirEntry;
infoBlockHdr picHeader = {
0, /* size of data block (get's filled in) */
4, {'M', 'A', 'I', 'N'},
0, /* master control word */
320, /* pixels per scan line */
1, /* number of pallettes */
{0,0,0,0,0,0,0,0,0,0,0,0,0,0}, /* pallette */
200 /* # of scan lines */
};
CreateRecGS createblk;
NameRecGS destroyblk;
OpenRecGS openblk;
IORecGS readblk;
IORecGS writeblk;
RefNumRecGS closeblk;
SetPositionRecGS setpositionblk;
typedef struct {
word slices;
word width;
char image[8 * 11];
char mask[8 * 11];
Point hotSpot;
} myCursor;
#define hotY 0
#define hotX 2
static myCursor cursor0 =
{ 11, 4, /* 0 */
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xf0,0x00,0x00,
0x00,0xf0,0xff,0xf0,0x00,0xff,0x00,0x00,
0x00,0xf0,0x00,0x00,0x00,0xf0,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xff,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
hotY, hotX };
static myCursor cursor1 =
{ 11, 4, /* 1 */
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xf0,0x00,0x0f,0x00,0x00,0x00,
0x00,0xf0,0x0f,0xf0,0x00,0xf0,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xff,0x00,0x00,
0x00,0xf0,0x00,0x00,0x00,0xf0,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xff,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
hotY, hotX };
static myCursor cursor2 =
{ 11, 4, /* 2 */
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0x00,0xf0,0x0f,0x00,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xf0,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xff,0x00,0x00,
0x00,0xf0,0x00,0x00,0x00,0xf0,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xff,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
hotY, hotX };
static myCursor cursor3 =
{ 11, 4, /* 3 */
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0x00,0x00,0xff,0x00,0x00,0x00,
0x00,0xf0,0x00,0xff,0x00,0xf0,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xff,0x00,0x00,
0x00,0xf0,0x00,0x00,0x00,0xf0,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xff,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
hotY, hotX };
static myCursor cursor4 =
{ 11, 4, /* 4 */
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xf0,0x00,0x00,
0x00,0xf0,0x00,0xff,0xf0,0xff,0x00,0x00,
0x00,0xf0,0x00,0x00,0x00,0xf0,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xff,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
hotY, hotX };
static myCursor cursor5 =
{ 11, 4, /* 5 */
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xf0,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xff,0x00,0x00,
0x00,0xf0,0x00,0x0f,0x00,0xf0,0x00,0x00,
0x00,0x0f,0x00,0x00,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xff,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
hotY, hotX };
static myCursor cursor6 =
{ 11, 4, /* 6 */
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xf0,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xff,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xf0,0x00,0x00,
0x00,0x0f,0x00,0xf0,0x0f,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xff,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
hotY, hotX };
static myCursor cursor7 =
{ 11, 4, /* 7 */
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0x00,0x00,0x0f,0x00,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xf0,0x00,0x00,
0x00,0xf0,0x00,0xf0,0x00,0xff,0x00,0x00,
0x00,0xf0,0x0f,0x00,0x00,0xf0,0x00,0x00,
0x00,0x0f,0xf0,0x00,0x0f,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
{ 0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xff,0x00,0x00,
0x00,0xff,0xff,0xff,0xff,0xf0,0x00,0x00,
0x00,0x0f,0xff,0xff,0xff,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00,
0x00,0x00,0xff,0xff,0xf0,0x00,0x00,0x00 },
hotY, hotX };
static myCursor *animCursor[8] = {&cursor0,&cursor1,&cursor2,&cursor3,&cursor4,&cursor5,&cursor6,&cursor7};
int SavePic(pathname, RefPtr)
GSString255 *pathname;
LocInfoPtr RefPtr;
{
extern int cTable[16];
char *invertBuf, *dummyBuf;
char *srcptr,*dstptr;
dirEntry *ScanLineDirectory; /* dynamic array */
unsigned cursNum = 0;
unsigned counter = 0;
unsigned linenum, srcSize, dstSize;
unsigned lineWidth, numLines;
unsigned i;
int errNum;
word oldSCB;
long totalSize;
WaitCursor();
lineWidth = RefPtr->width; /* get # of bytes per scan line */
numLines = RefPtr->boundsRect.v2 - RefPtr->boundsRect.v1; /* # of scan lines */
/* get memory for scan line directory array */
if(!(ScanLineDirectory = (dirEntry *) malloc(numLines * sizeof(dirEntry))))
return(0x54);
if(!(dstptr = malloc(lineWidth))) { /* allocate memory for converted scan line */
free(ScanLineDirectory);
return(0x54); /* return error condition */
}
if(!(invertBuf = malloc(lineWidth + 160))) { /* allocate memory for inverted scan line */
free(dstptr);
free(ScanLineDirectory);
return(0x54); /* return error condition */
}
destroyblk.pCount = closeblk.pCount = 1;
destroyblk.pathname = pathname;
DestroyGS(&destroyblk);
createblk.pCount = 4;
createblk.pathname = pathname;
createblk.access = 0xE3;
createblk.fileType = 0xC0;
createblk.auxType = 2;
CreateGS(&createblk);
if(errNum = /* assignment */ _toolErr)
goto goodbye2; /* messy, but efficient! */
openblk.pCount = 3;
openblk.pathname = pathname;
openblk.requestAccess = 2; /* write only */
OpenGS(&openblk);
if(errNum = /* assignment */ _toolErr)
goto goodbye2;
SetMasterSCB((oldSCB = GetMasterSCB()) | 0x0100); /* make sure cursor doesn't flicker */
setpositionblk.pCount = 3;
setpositionblk.refNum = closeblk.refNum = openblk.refNum;
setpositionblk.base = 0;
setpositionblk.displacement = totalSize = sizeof(picHeader) + (numLines * sizeof(dirEntry));
/* adjust EOF and mark past header fields of file */
SetEOFGS(&setpositionblk);
if(errNum = /* assignment */ _toolErr)
goto goodbye; /* messy, but efficient! */
SetMarkGS(&setpositionblk);
if(errNum = /* assignment */ _toolErr)
goto goodbye; /* messy, but efficient! */
writeblk.pCount = 4;
writeblk.refNum = openblk.refNum;
srcptr = RefPtr->ptrToPixImage; /* initialize source pointer */
writeblk.dataBuffer = dstptr;
for(linenum = 0; linenum < numLines; ++linenum) {
asm { /* invert the bytes of the scan line */
ldy #0 ; get the # of bytes in the line
ldx #0xFFFF ; inverse mask
sep #0x20 ; 8-bit accumulator
loop:
txa ; put inverse mask into accumulator
eor [srcptr],y ; get the byte and invert it
sta [invertBuf],y ; store in the destination buffer
iny
cpy lineWidth ; done yet?
bcc loop ; no...
#if 0
txa ; prepare to fill in remainder of scan line
loop2:
cpy #160 ; at least 320 pixels wide?
bcs done ; yes...
sta [invertBuf],y ; else fill it in
iny
bra loop2
done:
#endif
rep #0x20 ; back to 16-bit accumulator
}
srcptr += lineWidth; /* update source pointer */
srcSize = lineWidth; /* # of bytes per scan line */
dummyBuf = invertBuf; /* use temporary pointer for PackBytes */
dstSize = PackBytes(&dummyBuf,&srcSize,dstptr,lineWidth);
totalSize += dstSize; /* accumulate total size */
ScanLineDirectory[linenum].numBytes = dstSize;
ScanLineDirectory[linenum].modeWord = RefPtr->portSCB;
writeblk.requestCount = dstSize;
WriteGS(&writeblk);
if(errNum = /* assignment */ _toolErr)
goto goodbye; /* messy, but efficient! */
if(!(++counter & 7)) { /* update the cursor every eighth scan line processed */
SetCursor(animCursor[++cursNum]);
if(!(cursNum < 7)) /* in other words, if cursNum >= 7 (but this produces better code) */
cursNum = -1;
}
}
setpositionblk.displacement = 0; /* set file mark to beginning of file */
SetMarkGS(&setpositionblk);
if(errNum = /* assignment */ _toolErr)
goto goodbye; /* messy, but efficient! */
picHeader.blkSize = totalSize; /* fill in header fields */
picHeader.pixPerLine = RefPtr->width << (RefPtr->portSCB ? 2 : 1); /* pixels per line */
picHeader.scanLines = numLines; /* # of lines in image */
picHeader.mscb = RefPtr->portSCB; /* master SCB */
/* get the pallette into the header */
memcpy(picHeader.pallette,cTable,sizeof(picHeader.pallette));
writeblk.requestCount = sizeof(infoBlockHdr);
writeblk.dataBuffer = (Ptr) &picHeader;
WriteGS(&writeblk);
if(errNum = /* assignment */ _toolErr)
goto goodbye; /* messy, but efficient! */
writeblk.requestCount = numLines * sizeof(dirEntry);
writeblk.dataBuffer = (Ptr) ScanLineDirectory;
WriteGS(&writeblk);
if(errNum = /* assignment */ _toolErr)
goto goodbye; /* messy, but efficient! */
CloseGS(&closeblk);
errNum = _toolErr;
goodbye:
SetMasterSCB(oldSCB); /* reset master SCB */
closeblk.refNum = 0; /* do a global close */
CloseGS(&closeblk);
goodbye2:
free(invertBuf);
free(dstptr);
free(ScanLineDirectory);
InitCursor();
return(errNum);
}