pjs/dom/tools/FileGen.cpp

454 строки
12 KiB
C++

/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
*
* The contents of this file are subject to the Netscape Public
* License Version 1.1 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy of
* the License at http://www.mozilla.org/NPL/
*
* Software distributed under the License is distributed on an "AS
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
* implied. See the License for the specific language governing
* rights and limitations under the License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 1998 Netscape Communications Corporation. All
* Rights Reserved.
*
* Contributor(s):
*/
#include <stdio.h>
#include <fstream.h>
#include <ctype.h>
#include "plhash.h"
#include "FileGen.h"
#include "IdlSpecification.h"
#include "IdlObject.h"
#include "IdlVariable.h"
#include "IdlParameter.h"
#include "IdlAttribute.h"
#include "IdlFunction.h"
#include "IdlInterface.h"
static const char *kNPLStr = \
"/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-\n"
" *\n"
" * The contents of this file are subject to the Netscape Public\n"
" * License Version 1.1 (the \"License\"); you may not use this file\n"
" * except in compliance with the License. You may obtain a copy of\n"
" * the License at http://www.mozilla.org/NPL/\n"
" *\n"
" * Software distributed under the License is distributed on an \"AS\n"
" * IS\" basis, WITHOUT WARRANTY OF ANY KIND, either express or\n"
" * implied. See the License for the specific language governing\n"
" * rights and limitations under the License.\n"
" *\n"
" * The Original Code is mozilla.org code.\n"
" *\n"
" * The Initial Developer of the Original Code is Netscape\n"
" * Communications Corporation. Portions created by Netscape are\n"
" * Copyright (C) 1998 Netscape Communications Corporation. All\n"
" * Rights Reserved.\n"
" *\n"
" * Contributor(s): \n"
" */\n";
static const char *kDisclaimerStr = "/* AUTO-GENERATED. DO NOT EDIT!!! */\n";
static const char *kObjTypeStr = "nsIDOM%s*";
static const char *kUuidStr = "NS_IDOM%s_IID";
#ifdef USE_COMPTR
static const char *kObjTypePtrStr = "nsCOMPtr<nsIDOM%s>";
static const char *kXPIDLObjTypePtrStr = "nsCOMPtr<%s>";
#else
static const char *kObjTypePtrStr = "nsIDOM%sPtr";
static const char *kXPIDLObjTypePtrStr = "%sPtr";
#endif
static const char *kXPIDLObjTypeStr = "%s*";
static const char *kXPIDLUuidStr = "NS_I%s_IID";
FileGen::FileGen()
{
mOutputFile = new ofstream();
}
FileGen::~FileGen()
{
delete mOutputFile;
}
int
FileGen::OpenFile(char *aFileName, char *aOutputDirName,
const char *aFilePrefix, const char *aFileSuffix)
{
char file_buf[512];
if (aOutputDirName) {
strcpy(file_buf, aOutputDirName);
strcat(file_buf, "/");
}
else {
file_buf[0] = '\0';
}
strcat(file_buf, aFilePrefix);
strcat(file_buf, strtok(aFileName, "."));
strcat(file_buf, ".");
strcat(file_buf, aFileSuffix);
mOutputFile->open(file_buf);
return mOutputFile->is_open();
}
void
FileGen::CloseFile()
{
mOutputFile->close();
mOutputFile->clear();
}
void
FileGen::GenerateNPL()
{
*mOutputFile << kNPLStr;
*mOutputFile << kDisclaimerStr;
}
void
FileGen::GetVariableTypeForMethodLocal(char *aBuffer, IdlVariable &aVariable)
{
switch (aVariable.GetType()) {
case TYPE_BOOLEAN:
strcpy(aBuffer, "PRBool");
break;
case TYPE_LONG:
strcpy(aBuffer, "PRInt32");
break;
case TYPE_SHORT:
strcpy(aBuffer, "PRInt32");
break;
case TYPE_ULONG:
strcpy(aBuffer, "PRUint32");
break;
case TYPE_USHORT:
strcpy(aBuffer, "PRUint32");
break;
case TYPE_CHAR:
strcpy(aBuffer, "PRUint32");
break;
case TYPE_INT:
strcpy(aBuffer, "PRInt32");
break;
case TYPE_UINT:
strcpy(aBuffer, "PRUint32");
break;
case TYPE_STRING:
strcpy(aBuffer, "nsAutoString");
break;
case TYPE_OBJECT:
sprintf(aBuffer, kObjTypePtrStr, aVariable.GetTypeName());
break;
case TYPE_XPIDL_OBJECT:
sprintf(aBuffer, kXPIDLObjTypePtrStr, aVariable.GetTypeName());
break;
case TYPE_FUNC:
sprintf(aBuffer, kObjTypePtrStr, aVariable.GetTypeName());
break;
case TYPE_JSVAL:
strcpy(aBuffer, "jsval");
break;
default:
// XXX Fail for other cases
break;
}
}
void
FileGen::GetVariableTypeForLocal(char *aBuffer, IdlVariable &aVariable)
{
switch (aVariable.GetType()) {
case TYPE_BOOLEAN:
strcpy(aBuffer, "PRBool");
break;
case TYPE_LONG:
strcpy(aBuffer, "PRInt32");
break;
case TYPE_SHORT:
strcpy(aBuffer, "PRInt16");
break;
case TYPE_ULONG:
strcpy(aBuffer, "PRUint32");
break;
case TYPE_USHORT:
strcpy(aBuffer, "PRUint16");
break;
case TYPE_CHAR:
strcpy(aBuffer, "PRUint8");
break;
case TYPE_INT:
strcpy(aBuffer, "PRInt32");
break;
case TYPE_UINT:
strcpy(aBuffer, "PRUint32");
break;
case TYPE_STRING:
strcpy(aBuffer, "nsAutoString");
break;
case TYPE_OBJECT:
sprintf(aBuffer, kObjTypeStr, aVariable.GetTypeName());
break;
case TYPE_XPIDL_OBJECT:
sprintf(aBuffer, kXPIDLObjTypeStr, aVariable.GetTypeName());
break;
case TYPE_FUNC:
sprintf(aBuffer, kObjTypeStr, aVariable.GetTypeName());
break;
case TYPE_JSVAL:
strcpy(aBuffer, "jsval");
break;
default:
// XXX Fail for other cases
break;
}
}
void
FileGen::GetVariableTypeForParameter(char *aBuffer, IdlVariable &aVariable)
{
switch (aVariable.GetType()) {
case TYPE_BOOLEAN:
strcpy(aBuffer, "PRBool");
break;
case TYPE_LONG:
strcpy(aBuffer, "PRInt32");
break;
case TYPE_SHORT:
strcpy(aBuffer, "PRInt16");
break;
case TYPE_ULONG:
strcpy(aBuffer, "PRUint32");
break;
case TYPE_USHORT:
strcpy(aBuffer, "PRUint16");
break;
case TYPE_CHAR:
strcpy(aBuffer, "PRUint8");
break;
case TYPE_INT:
strcpy(aBuffer, "PRInt32");
break;
case TYPE_UINT:
strcpy(aBuffer, "PRUint32");
break;
case TYPE_STRING:
strcpy(aBuffer, "nsString&");
break;
case TYPE_OBJECT:
sprintf(aBuffer, kObjTypeStr, aVariable.GetTypeName());
break;
case TYPE_XPIDL_OBJECT:
sprintf(aBuffer, kXPIDLObjTypeStr, aVariable.GetTypeName());
break;
case TYPE_FUNC:
sprintf(aBuffer, kObjTypeStr, aVariable.GetTypeName());
break;
case TYPE_JSVAL:
strcpy(aBuffer, "jsval");
break;
default:
// XXX Fail for other cases
break;
}
}
void
FileGen::GetParameterType(char *aBuffer, IdlParameter &aParameter)
{
GetVariableTypeForParameter(aBuffer, aParameter);
switch (aParameter.GetAttribute()) {
case IdlParameter::INPUT:
if (aParameter.GetType() == TYPE_STRING) {
char buf[256];
strcpy(buf, "const ");
strcat(buf, aBuffer);
strcpy(aBuffer, buf);
}
break;
case IdlParameter::OUTPUT:
case IdlParameter::INOUT:
if (aParameter.GetType() != TYPE_STRING) {
strcat (aBuffer, "*");
}
break;
}
}
void
FileGen::GetInterfaceIID(char *aBuffer, char *aInterfaceName)
{
char buf[256];
strcpy(buf, aInterfaceName);
StrUpr(buf);
sprintf(aBuffer, kUuidStr, buf);
}
void
FileGen::GetInterfaceIID(char *aBuffer, IdlInterface &aInterface)
{
GetInterfaceIID(aBuffer, aInterface.GetName());
}
void
FileGen::GetXPIDLInterfaceIID(char* aBuffer, char* aInterfaceName)
{
char buf[256];
strcpy(buf, aInterfaceName);
StrUpr(buf);
sprintf(aBuffer, kXPIDLUuidStr, buf);
}
void
FileGen::GetXPIDLInterfaceIID(char* aBuffer, IdlInterface &aInterface)
{
GetInterfaceIID(aBuffer, aInterface.GetName());
}
void
FileGen::GetCapitalizedName(char *aBuffer, IdlObject &aObject)
{
strcpy(aBuffer, aObject.GetName());
if ((aBuffer[0] >= 'a') && (aBuffer[0] <= 'z')) {
aBuffer[0] += ('A' - 'a');
}
}
void
FileGen::StrUpr(char *aBuffer)
{
char *cur_ptr = aBuffer;
while (*cur_ptr != 0) {
if ((*cur_ptr >= 'a') && (*cur_ptr <= 'z')) {
*cur_ptr += ('A' - 'a');
}
cur_ptr++;
}
}
void
FileGen::StrLwr(char *aBuffer)
{
char *cur_ptr = aBuffer;
while (*cur_ptr != 0) {
if ((*cur_ptr >= 'A') && (*cur_ptr <= 'Z')) {
*cur_ptr += ('a' - 'A');
}
cur_ptr++;
}
}
void
FileGen::CollectAllInInterface(IdlInterface &aInterface,
PLHashTable *aTable)
{
int a, acount = aInterface.AttributeCount();
for (a = 0; a < acount; a++) {
IdlAttribute *attr = aInterface.GetAttributeAt(a);
if (((attr->GetType() == TYPE_OBJECT) || (attr->GetType() == TYPE_XPIDL_OBJECT)) &&
!PL_HashTableLookup(aTable, attr->GetTypeName())) {
PL_HashTableAdd(aTable, attr->GetTypeName(), (void *)(attr->GetType()));
}
}
int m, mcount = aInterface.FunctionCount();
for (m = 0; m < mcount; m++) {
IdlFunction *func = aInterface.GetFunctionAt(m);
IdlVariable *rval = func->GetReturnValue();
if (((rval->GetType() == TYPE_OBJECT) || (rval->GetType() == TYPE_XPIDL_OBJECT)) &&
!PL_HashTableLookup(aTable, rval->GetTypeName())) {
PL_HashTableAdd(aTable, rval->GetTypeName(), (void *)(rval->GetType()));
}
int p, pcount = func->ParameterCount();
for (p = 0; p < pcount; p++) {
IdlParameter *param = func->GetParameterAt(p);
if (((param->GetType() == TYPE_OBJECT) || (param->GetType() == TYPE_XPIDL_OBJECT)
|| (param->GetType() == TYPE_FUNC)) && !PL_HashTableLookup(aTable, param->GetTypeName())) {
PL_HashTableAdd(aTable, param->GetTypeName(), (void *)(param->GetType()));
}
}
}
}
void
FileGen::EnumerateAllObjects(IdlInterface &aInterface,
PLHashEnumerator aEnumerator,
void *aArg)
{
PLHashTable *htable = PL_NewHashTable(10, PL_HashString,
PL_CompareStrings,
PL_CompareValues,
(PLHashAllocOps *)NULL, NULL);
CollectAllInInterface(aInterface, htable);
PL_HashTableEnumerateEntries(htable, aEnumerator, aArg);
PL_HashTableDestroy(htable);
}
void
FileGen::EnumerateAllObjects(IdlSpecification &aSpec,
PLHashEnumerator aEnumerator,
void *aArg,
PRBool aOnlyPrimary)
{
PLHashTable *htable = PL_NewHashTable(10, PL_HashString,
PL_CompareStrings,
PL_CompareValues,
(PLHashAllocOps *)NULL, NULL);
int i, icount = aSpec.InterfaceCount();
for (i = 0; i < icount; i++) {
IdlInterface *iface = aSpec.GetInterfaceAt(i);
if (((i == 0) || !aOnlyPrimary) &&
!PL_HashTableLookup(htable, iface->GetName())) {
PL_HashTableAdd(htable, iface->GetName(), (void *)(int)TYPE_OBJECT);
}
CollectAllInInterface(*iface, htable);
}
PL_HashTableEnumerateEntries(htable, aEnumerator, aArg);
PL_HashTableDestroy(htable);
}
PRBool
FileGen::HasConstructor(IdlInterface &aInterface, IdlFunction **aConstructor)
{
int m, mcount = aInterface.FunctionCount();
for (m = 0; m < mcount; m++) {
IdlFunction *func = aInterface.GetFunctionAt(m);
if (strcmp(func->GetName(), aInterface.GetName()) == 0) {
if (NULL != aConstructor) {
*aConstructor = func;
}
return PR_TRUE;
}
}
return PR_FALSE;
}