🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: comp.os.ms-windows.programmer.misc
Article #2806

Help: XLL programming problem...

#2806
From: guthrie
Date: Wed, 30 Aug 1995 03:31
401 lines
10601 bytes
Summary: trying simple .XLL example, get odd illogical C-code effects; 
is it a compiler bug??
------------------------------------------------

I am writing my first Excel DLL, and got it to work fine.   :-)

But, to make it into an .XLL I am starting with a sample (From 
Compuserve..) called poly.xll, which GPFs whenever I try it. This 
sample was distributed with a Borland compiled binary, and source 
code. The binary works, but a recompiled Msoft.VC++ (1.50) version 
GPFs.

The sample is nearly a clone of the Excel SDK examples (which do 
work..), and in debugging it I get a really mysterious error.

Basically, the function registration name table is a static global, 
and in LibMain (as always) it gets LPSTR'ed.

But, the next routine of mine that is called is xlAutoOpen, and in the 
first statement of that routine I can no longer access the addresses 
of the entries in this table. A piece of identical test code in each 
of these two routines, 
		char* atest = rgFuncs[0][6];   /* Test */

gets different values when accessing the rgFuncs[0][i] values. One 
could suspect that somehow they got clobbered in the interim, but 
not-so, one can look at the right-hand-side of the test statement 
(debugger/watch), and it is OK, only the value is not accessed 
properly. This same bad effect occurs when these (correct global) 
values are passed to TmpStr(), which is the cause of the original GPF.

This looks like a compiler bug to me, but seems so odd that I thought 
I should seek some other advice/opinions.

Any ideas appreciated!!

Gregory Guthrie

attachments: 1) debugging summary;
             2) full code of failing routine.
-===================================================================--
----------------------------------
// structure containing function registration info
// see MS Excel SDK for additional details
static LPSTR rgFuncs[rgFuncsRows][7] =
{
	{" Poly2",           " EEEEE",      " Poly2"," ", " 1", " ", " 
"}
};
---------------------------------------------------------------------
int FAR PASCAL LibMain(HANDLE hInstance, WORD wDataSeg,
			  WORD wHeapSize, LPSTR lpszCmdLine)
{
	 static int i,j;
	
         char* atest = rgFuncs[0][6];   /* Test */

	 			/** byte count local strings. **/
	 for (i=0; i<rgFuncsRows; i++)
	 {
		for (j=0; j<7; j++)
		{
         atest = rgFuncs[i][j];   /* Test : good */
		 rgFuncs[i][j][0] = (BYTE) lstrlen (rgFuncs[i][j]+1);
		}
	 }

  	 InitFramework();
	 return 1;
}
---------------------------------------------------------------------

int FAR PASCAL xlAutoOpen(void)
{
	 char tmp[512]="\0";
	 static XLOPER   xDLL;             /* name of this DLL */
	 int             i;                /* Loop index */

         char* btest = rgFuncs[0][6];   /* Test : RHS=good, LHS=bad */
         LPSTR ctest = rgFuncs[0][6];   /* Test : RHS=good, LHS=bad */

	 Excel(xlGetName, &xDLL, 0);
	 for (i=0; i<rgFuncsRows; i++){
	 Excel(xlfRegister, 0, 8,
		  (LPXLOPER) &xDLL,
		  (LPXLOPER) TempStr(rgFuncs[i][0]),
		  (LPXLOPER) TempStr(rgFuncs[i][1]),
		  (LPXLOPER) TempStr(rgFuncs[i][2]),
		  (LPXLOPER) TempStr(rgFuncs[i][3]),
		  (LPXLOPER) TempStr(rgFuncs[i][4]),
		  (LPXLOPER) TempStr(rgFuncs[i][5]),
		  (LPXLOPER) TempStr(rgFuncs[i][6]));
	 }
---------------------------------------------------------------------
atest = CXX0030: Error: expression cannot be evaluated
+btest = 0x0001:0x0001 ""                         <-------bad
+ctest = 0x0001:0x0001 ""
-rgFuncs[0][6] = 0x39A7:0x002C ""                 <-------good
    = 0 ''
--------------------------------------------------------------------
LPXLOPER TempStr(LPSTR lpstr)
{
    LPXLOPER lpx;

    char* atest = lpstr;   /* Test : bad */
    LPSTR ctest = lpstr;   /* Test : bad */
    .......
-===================================================================--
b) Full code of failing example follows:

/*
**  poly.xll
**
**  This source code demonstrates how to create a VERY simple
**  Excel Add-In (*.XLL).  In this example the function "Poly2"
**  evaluates a 2nd-order polynomial given x and the coeficients
**  a, b, and c.
**
**  Poly2(x,a,b,c) returns a*x^2 + b*x + c
**
**  The following code takes advantage of MUCH code (GENERIC.C)
**  supplied with "MICROSOFT EXCEL SOFTWARE DEVELOPMENT KIT."
**  You will need the following files:
**
**     framewrk.c  (supplied with MS Excel SDK)
**                 There's a new file on CIS, I believe with the
**                 same name.  It fixes a problem with xlCoerce.
**                 It is not necessary for this demo.
**
**     xlcall.dll  (supplied with Excel)
**     xlcall.lib  (supplied with MS Excel SDK)
**                 You may need to create this file with
**                 a tool such as implib supplied with BC++.
**                 It seems reasonable that this may only
**                 be necessary for non-MS compilers/linkers.
**                 If you really want to know, ask an expert.
**
**
**
**  bob walker
*/

#define XLLNAME  "Sample EXCEL Add-In"
#define LASTREV  "1/28/95"


#define FUNC1 Poly2
#define NAME1 " Poly2"

// For some reason???  The following macro is NOT required
// when compiling with Turbo C++ 3.1
#define LPDOUBLE double*


#include <ctype.h>
#include <string.h>
#include <windows.h>
#include <xlcall.h>      // supplied by MS EXCEL SDK
#include "framewrk.h"    // supplied by MS EXCEL SDK

#define rgFuncsRows 1


// function prototype for exported function Poly2()
LPDOUBLE FAR PASCAL FUNC1(LPDOUBLE x,
							  LPDOUBLE a,
							  LPDOUBLE b,
							  LPDOUBLE c);


// structure containing function registration info
// see MS Excel SDK for additional details
static LPSTR rgFuncs[rgFuncsRows][7] =
{
	{" Poly2",           " EEEEE",      " Poly2"," ", " 1", " ", " 
"}
};


// the Poly2() function
// looks odd, I know
LPDOUBLE FAR PASCAL FUNC1(LPDOUBLE x,
							  LPDOUBLE a,
							  LPDOUBLE b,
							  LPDOUBLE c)
{
  static double y;
  y=(*a)*(*x)*(*x)+(*b)*(*x)+(*c);
  return (LPDOUBLE) &y;
}


/*============================================================*/


/*
** LibMain
*/

#pragma argsused                                          
int FAR PASCAL LibMain(HANDLE hInstance, WORD wDataSeg,
			  WORD wHeapSize, LPSTR lpszCmdLine)
{
	 static int i,j; 
	 
         char* atest = rgFuncs[0][6];   /* Test */

	 			/** byte count local strings..
				 **/
	 for (i=0; i<rgFuncsRows; i++)
	 {
		for (j=0; j<7; j++)
		{        
         atest = rgFuncs[i][j];   /* Test */
 
			 rgFuncs[i][j][0] = (BYTE) lstrlen 
(rgFuncs[i][j]+1);
		}
	 }

	 InitFramework();
	 return 1;
}


/*
** WEP
*/

#pragma argsused
int FAR PASCAL WEP (int nArgument)
{
	 return 1;
}




/*
** xlAutoOpen
**  return 1 if successful, or return 0 if your XLL cannot be opened.
*/

int FAR PASCAL xlAutoOpen(void)
{
	 char tmp[512]="\0";
	 static XLOPER   xDLL;             /* name of this DLL */
	 int             i;                /* Loop index */
         
         char* btest = rgFuncs[0][6];   /* Test */
         LPSTR ctest = rgFuncs[0][6];   /* Test */
         
	 Excel(xlGetName, &xDLL, 0);
	 for (i=0; i<rgFuncsRows; i++){
	 Excel(xlfRegister, 0, 8,
		  (LPXLOPER) &xDLL,
		  (LPXLOPER) TempStr(rgFuncs[i][0]),
		  (LPXLOPER) TempStr(rgFuncs[i][1]),
		  (LPXLOPER) TempStr(rgFuncs[i][2]),
		  (LPXLOPER) TempStr(rgFuncs[i][3]),
		  (LPXLOPER) TempStr(rgFuncs[i][4]),
		  (LPXLOPER) TempStr(rgFuncs[i][5]),
		  (LPXLOPER) TempStr(rgFuncs[i][6]));
	 }

	 Excel(xlFree, 0, 1, (LPXLOPER) &xDLL);

	 strcat(tmp, " Congratulations!\n");
	 strcat(tmp,"Poly.Xll has been loaded -- .\n\n");
	 strcat(tmp,"Poly2(x,a,b,c)=a*x^2+bx+c\n");
	 tmp[0]=strlen(tmp)-1;
	 Excel(xlcAlert, 0, 2, TempStr(tmp), TempInt(2));

	 return 1;
}


/*
** xlAutoClose
** should return 1.
*/

int FAR PASCAL xlAutoClose(void)
{
	 int i;

	 for (i=0; i<rgFuncsRows; i++){
		Excel(xlfSetName, 0, 1, TempStr(rgFuncs[i][2]));
	 }

	 return 1;
}


/*
** lpstricmp
*/

int PASCAL lpstricmp(LPSTR s, LPSTR t)
{
	 int i;

	 if (*s != *t) return 1;

	 for (i=1; i<=s[0]; i++){
		if (tolower(s[i]) != tolower(t[i])){
		  return 1;
		}
	 }

	 return 0;
}


/*
** xlAutoRegister
*/

LPXLOPER FAR PASCAL xlAutoRegister(LPXLOPER pxName)
{
	 static XLOPER xDLL, xRegId;
	 int i;

	 xRegId.xltype = xltypeErr;
	 xRegId.val.err = xlerrValue;


	 for (i=0; i<rgFuncsRows; i++){
		if (!lpstricmp(rgFuncs[i][0], pxName->val.str)){
		  Excel(xlGetName, &xDLL, 0);

		  Excel(xlfRegister, 0, 8,
			 (LPXLOPER) &xDLL,
			 (LPXLOPER) TempStr(rgFuncs[i][0]),
			 (LPXLOPER) TempStr(rgFuncs[i][1]),
			 (LPXLOPER) TempStr(rgFuncs[i][2]),
			 (LPXLOPER) TempStr(rgFuncs[i][3]),
			 (LPXLOPER) TempStr(rgFuncs[i][4]),
			 (LPXLOPER) TempStr(rgFuncs[i][5]),
			 (LPXLOPER) TempStr(rgFuncs[i][6]));

			 Excel(xlFree, 0, 1, (LPXLOPER) &xDLL);

			 return (LPXLOPER) &xRegId;
		}
	 }

	return (LPXLOPER) &xRegId;
}


/*
** xlAutoAdd
*/

int FAR PASCAL xlAutoAdd(void)
{
 /* Display a dialog box indicating that the XLL was successfully 
added */
	 Excel(xlcAlert, 0, 2, TempStr(" Thank you for adding Poly 
XLL!"),
		TempInt(2));
	 return 1;
}


/*
** xlAutoRemove
*/

int FAR PASCAL xlAutoRemove(void)
{
 /* Display a dialog box indicating that the XLL was successfully 
removed */
	 Excel(xlcAlert, 0, 2, TempStr(" Thank you for removing Poly 
XLL!"),
		TempInt(2));
	 return 1;
}


/* xlAddInManagerInfo
**
*/

LPXLOPER FAR PASCAL xlAddInManagerInfo(LPXLOPER xAction)
{
	 static XLOPER xInfo, xIntAction;
	 Excel(xlCoerce, &xIntAction, 2, xAction, TempInt(xltypeInt));

	 if(xIntAction.val.w==1){
		xInfo.xltype = xltypeStr;
		xInfo.val.str = "\026POLY SAMPLE        DLL";
	 }
	 else{
		xInfo.xltype = xltypeErr;
		xInfo.val.err = xlerrValue;
	 }
	 return (LPXLOPER) &xInfo;
}
Technical Details
Message-ID: <NEWTNews.809733745.20813.guthrie@csgrg.miu.edu>
Path: arc1-ca.pugleaf.net!news.iastate.edu!usenet

Show Full Headers
Complete Article Headers
Path: arc1-ca.pugleaf.net!news.iastate.edu!usenet
From: guthrie@miu.edu
Newsgroups: comp.os.ms-windows.programmer.misc,comp.lang.c,comp.apps.spreadsheets
Subject: Help: XLL programming problem...
Date: Tue, 29 Aug 95 22:31:13 CDT
Organization: Iowa State University, Ames, Iowa
Message-ID: <NEWTNews.809733745.20813.guthrie@csgrg.miu.edu>
NNTP-Posting-Host: csgrg.miu.edu
Mime-Version: 1.0
Content-Type: TEXT/PLAIN; charset=US-ASCII
To: jprice@miu.edu, guthrie
X-Newsreader: NEWTNews & Chameleon -- TCP/IP for MS Windows from NetManage