[comp.sys.mac.programmer] Need help with XCMD's and THINK C 4.0

dmr@csli.Stanford.EDU (Daniel M. Rosenberg) (10/12/90)

Help!

We're trying to implement an XCMD in THINK C 4.0, and have followed
the examples from the "How to build XCMD's in HyperCard book" as
closely as possible.

It compiles and runs fine (thanks to getting the XCMD glue stuff direct
from Symantec) but when it runs and does some file i/o and grabbing
memory through NewHandle (and yes, we locked the handles down) the screen
fills with green crud and the machine crashes. The XCMD code runs fine
as a standalone program.

Does anyone have any hints, or, better yet, example code in Think C 4.0?

We're stuck, frustrated, and desperate!

Thanks for any help you can provide --


-- 
# Daniel M. Rosenberg    //  Stanford CSLI  // Chew my opinions, not Stanford's.
# dmr@csli.stanford.edu // decwrl!csli!dmr // dmr%csli@stanford.bitnet

oster@well.sf.ca.us (David Phillip Oster) (10/14/90)

In article <15784@csli.Stanford.EDU> dmr@csli.Stanford.EDU (Daniel M. Rosenberg) writes:
>We're trying to implement an XCMD in THINK C 4.0, and have followed
>the examples from the "How to build XCMD's in HyperCard book" as
>closely as possible.
Enclosed is the root of an XFCN I wrote. It implements an interface to
a proprietary file format, performaing many different functions, 
using the first argument as a function selector. Note the use of RememberA0(),
SetUpA4(). this is critical if you use any literal strings, since THINK C
references these off of its global pointer. (At least THINK C v.3 did.)
Sorry about the slightly non-standard nomenclature. When I sat down to write
this I discovered my Hypercard interface had succumbed to software root, so
I had to reconstruct it based on the HyperCard Script Langauge Guide.
This _IS_ verbatim quotes from working code that does file i/o, however.

#include <SetUpA4.h>
#include <HyperXCmd.h>

/* main - 
 */
pascal void main(xp)XCmdPtr xp;{
	RememberA0();
	SetUpA4();

	switch(ParamToNum(xp, 0)){
	case ABVERSION:		AFileVersion(xp);			break;
	case ABOPEN:		AFileOpen(xp);				break;
	case ABCOUNTRECS:	AFileCountRecs(xp);			break;
	case ABREADFIELD:	AFileReadField(xp);			break;
	case ABCLOSE:		AFileClose(xp);				break;
	case ABREADFIELDNAME:	AFileReadFieldName(xp);		break;
	case ABCOUNTFIELDNAMES:	AFileCountFieldnames(xp);	break;
	case ABSIGNATURE:	AFileSignature(xp);			break;
	case ABMASTERID:	AFileMasterID(xp);			break;
	case ABCURRENTSORT:	AFileCurrentSort(xp);		break;
	}

	RestoreA4();
}

#define private static
typedef long  LongInt;
typedef short Integer;

/* ParamToNum - given a parameter that should be numeric, return it.
 */
private LongInt ParamToNum(XCmdPtr xp, Integer n){
	Str255	s;
	LongInt	val;

	if(n >= xp->paramCount){
		return 0;
	}
	ZeroToPas(xp, *(xp->params[n]), s);
	val = StrToNum(xp, s);
	return (xresSucc == xp->result) ? val : 0;
}

/* ZeroToPas - write zeroes into memory
 */
pascal void ZeroToPas(XCmdPtr xp, char *zeroStr, StringPtr s){
	xp->inArgs[0] = (LongInt) zeroStr;
	xp->inArgs[1] = (LongInt) s;
	xp->request = xreqZeroToPas;
	(*xp->entryPoint)();
}
-- 
-- David Phillip Oster - Note new signature. Old one has gone Bye Bye.
-- oster@well.sf.ca.us = {backbone}!well!oster