aboutsummaryrefslogtreecommitdiff
path: root/SrcShared/LoadApplication.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'SrcShared/LoadApplication.cpp')
-rw-r--r--SrcShared/LoadApplication.cpp381
1 files changed, 381 insertions, 0 deletions
diff --git a/SrcShared/LoadApplication.cpp b/SrcShared/LoadApplication.cpp
new file mode 100644
index 0000000..f3c8211
--- /dev/null
+++ b/SrcShared/LoadApplication.cpp
@@ -0,0 +1,381 @@
+/* -*- mode: C++; tab-width: 4 -*- */
+/* ===================================================================== *\
+ Copyright (c) 1998-2001 Palm, Inc. or its subsidiaries.
+ All rights reserved.
+
+ This file is part of the Palm OS Emulator.
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+\* ===================================================================== */
+
+#include "EmCommon.h"
+#include "LoadApplication.h"
+
+#include "EmErrCodes.h" // kError_OutOfMemory
+#include "EmMemory.h" // EmMem_memcpy
+#include "EmPalmStructs.h" // RecordEntryType, RsrcEntryType, etc.
+#include "EmStreamFile.h" // EmStreamFile
+#include "ErrorHandling.h" // Errors::ThrowIfPalmError
+#include "Miscellaneous.h" // StMemory
+#include "ROMStubs.h" // DmFindDatabase, DmGetLastErr, DmDatabaseInfo, DmOpenDatabase, ...
+#include "Strings.r.h" // kStr_ values
+
+
+static Bool PrvIsResources (UInt16 attributes)
+{
+ return (attributes & dmHdrAttrResDB);
+}
+
+
+/************************************************************
+ * Export a resource or record database as a normal data file in
+ * Pilot format.
+ *************************************************************/
+
+static void PrvMyShlExportAsPilotFile(EmStreamFile& fh, UInt16 cardNo, const char* nameP)
+{
+ DmOpenRef dbP = 0;
+ Err err;
+ UInt16 numRecords;
+ int size;
+ long offset;
+ int i;
+
+ try
+ {
+ //------------------------------------------------------------
+ // Locate the Database and see what kind of database it is
+ //------------------------------------------------------------
+
+ LocalID dbID;
+ dbID = ::DmFindDatabase (cardNo, (Char*) nameP);
+ if (!dbID)
+ Errors::ThrowIfPalmError (::DmGetLastErr ());
+
+ UInt16 attributes, version;
+ UInt32 crDate, modDate, bckUpDate;
+ UInt32 type, creator;
+ UInt32 modNum;
+ LocalID appInfoID, sortInfoID;
+ const int kGapSize = 2;
+
+ err = ::DmDatabaseInfo (cardNo, dbID, 0,
+ &attributes, &version, &crDate,
+ &modDate, &bckUpDate,
+ &modNum, &appInfoID,
+ &sortInfoID, &type,
+ &creator);
+ Errors::ThrowIfPalmError(err);
+
+ dbP = ::DmOpenDatabase (cardNo, dbID, dmModeReadOnly);
+ if (!dbP)
+ Errors::ThrowIfPalmError (::DmGetLastErr ());
+
+ //------------------------------------------------------------
+ // Write out a resource database
+ //------------------------------------------------------------
+ if (::PrvIsResources (attributes))
+ {
+ DmResType resType;
+ DmResID resID;
+ UInt32 resSize;
+
+ numRecords = ::DmNumRecords(dbP);
+
+ size = EmAliasDatabaseHdrType<LAS>::GetSize () + numRecords * EmAliasRsrcEntryType<LAS>::GetSize () + kGapSize;
+ StMemory outP (size, true);
+
+ // Fill in header
+ EmAliasDatabaseHdrType<LAS> hdr (outP.Get ());
+
+ strcpy ((char*) hdr.name.GetPtr (), nameP);
+ hdr.attributes = attributes;
+ hdr.version = version;
+ hdr.creationDate = crDate;
+ hdr.modificationDate = modDate;
+ hdr.lastBackupDate = bckUpDate;
+ hdr.modificationNumber = modNum;
+ hdr.appInfoID = 0;
+ hdr.sortInfoID = 0;
+ hdr.type = type;
+ hdr.creator = creator;
+
+ hdr.recordList.nextRecordListID = 0;
+ hdr.recordList.numRecords = numRecords;
+
+ // Get the size of the appInfo and sort Info if they exist
+ offset = size;
+ MemHandle appInfoH=0, sortInfoH=0;
+ UInt32 appInfoSize=0, sortInfoSize=0;
+ if (appInfoID)
+ {
+ hdr.appInfoID = offset;
+ appInfoH = (MemHandle) ::MemLocalIDToGlobal (appInfoID, cardNo);
+ if (!appInfoH)
+ {
+ Errors::ThrowIfPalmError (-1);
+ }
+ appInfoSize = ::MemHandleSize (appInfoH);
+ offset += appInfoSize;
+ }
+
+ if (sortInfoID)
+ {
+ hdr.sortInfoID = offset;
+ sortInfoH = (MemHandle) ::MemLocalIDToGlobal (sortInfoID, cardNo);
+ if (!sortInfoH)
+ {
+ Errors::ThrowIfPalmError (-1);
+ }
+ sortInfoSize = ::MemHandleSize (sortInfoH);
+ offset += sortInfoSize;
+ }
+
+
+ // Fill in the info on each resource into the header
+ offset = size;
+ for (i=0; i < numRecords; i++)
+ {
+ EmAliasRsrcEntryType<LAS> entry (hdr.recordList.resources[i]);
+
+ ::DmResourceInfo (dbP, i, &resType, &resID, NULL);
+ MemHandle resH = ::DmGetResourceIndex (dbP, i);
+ if (resH)
+ {
+ resSize = ::MemHandleSize (resH);
+ ::DmReleaseResource (resH);
+ }
+ else
+ {
+ resSize = 0;
+ }
+
+ entry.type = resType;
+ entry.id = resID;
+ entry.localChunkID = offset;
+
+ offset += resSize;
+ }
+
+ // Clear out gap
+ if (kGapSize > 0)
+ memset (outP.Get() + (size - kGapSize), 0, kGapSize);
+
+ // Write out entry table
+ fh.PutBytes (outP.Get (), size);
+
+ // Write out the appInfo followed by sortInfo, if they exist
+ if (appInfoID && appInfoSize)
+ {
+ UInt32 srcP;
+ StMemory outP (appInfoSize);
+ srcP = (UInt32) ::MemHandleLock (appInfoH);
+ EmMem_memcpy ((void*) outP.Get(), srcP, appInfoSize);
+ ::MemPtrUnlock ((MemPtr) srcP);
+ fh.PutBytes (outP.Get (), appInfoSize);
+ }
+
+ if (sortInfoID && sortInfoSize)
+ {
+ UInt32 srcP;
+ StMemory outP (sortInfoSize);
+ srcP = (UInt32) ::MemHandleLock (sortInfoH);
+ EmMem_memcpy ((void*) outP.Get(), srcP, sortInfoSize);
+ ::MemPtrUnlock ((MemPtr) srcP);
+ fh.PutBytes (outP.Get (), sortInfoSize);
+ }
+
+ // Write out each resource
+ for (i=0; i < numRecords; i++)
+ {
+ MemHandle srcResH;
+ LocalID resChunkID;
+
+ ::DmResourceInfo (dbP, i, &resType, &resID, &resChunkID);
+
+ if (resChunkID)
+ {
+ UInt32 srcP;
+ srcResH = ::DmGetResourceIndex (dbP, i);
+ if (!srcResH)
+ {
+ Errors::ThrowIfPalmError (-1);
+ }
+ resSize = ::MemHandleSize (srcResH);
+
+ StMemory outP (resSize);
+ srcP = (UInt32) ::MemHandleLock (srcResH);
+ EmMem_memcpy ((void*) outP.Get (), srcP, resSize);
+ ::MemPtrUnlock ((MemPtr) srcP);
+ fh.PutBytes (outP.Get (), resSize);
+
+ ::DmReleaseResource (srcResH);
+ }
+ }
+ } // Resource database
+
+ //------------------------------------------------------------
+ // Write out a records database
+ //------------------------------------------------------------
+ else
+ {
+ UInt16 attr;
+ UInt32 uniqueID;
+ MemHandle srcH;
+
+ numRecords = ::DmNumRecords (dbP);
+
+ size = EmAliasDatabaseHdrType<LAS>::GetSize () + numRecords * EmAliasRecordEntryType<LAS>::GetSize () + kGapSize;
+ StMemory outP(size);
+
+ // Fill in header
+ EmAliasDatabaseHdrType<LAS> hdr (outP.Get ());
+
+ strcpy ((char*) hdr.name.GetPtr (), nameP);
+ hdr.attributes = attributes;
+ hdr.version = version;
+ hdr.creationDate = crDate;
+ hdr.modificationDate = modDate;
+ hdr.lastBackupDate = bckUpDate;
+ hdr.modificationNumber = modNum;
+ hdr.appInfoID = 0;
+ hdr.sortInfoID = 0;
+ hdr.type = type;
+ hdr.creator = creator;
+
+ hdr.recordList.nextRecordListID = 0;
+ hdr.recordList.numRecords = numRecords;
+
+
+ // Get the size of the appInfo and sort Info if they exist
+ offset = size;
+ MemHandle appInfoH=0, sortInfoH=0;
+ UInt32 appInfoSize=0, sortInfoSize=0;
+ if (appInfoID)
+ {
+ hdr.appInfoID = offset;
+ appInfoH = (MemHandle) ::MemLocalIDToGlobal (appInfoID, cardNo);
+ if (!appInfoH)
+ {
+ Errors::ThrowIfPalmError (-1);
+ }
+ appInfoSize = ::MemHandleSize (appInfoH);
+ offset += appInfoSize;
+ }
+
+ if (sortInfoID)
+ {
+ hdr.sortInfoID = offset;
+ sortInfoH = (MemHandle) ::MemLocalIDToGlobal (sortInfoID, cardNo);
+ if (!sortInfoH)
+ {
+ Errors::ThrowIfPalmError (-1);
+ }
+ sortInfoSize = ::MemHandleSize (sortInfoH);
+ offset += sortInfoSize;
+ }
+
+
+ // Fill in the info on each resource into the header
+ for (i=0; i < numRecords; i++)
+ {
+ EmAliasRecordEntryType<LAS> entry (hdr.recordList.records[i]);
+
+ err = ::DmRecordInfo (dbP, i, &attr, &uniqueID, 0);
+ if (err)
+ {
+ Errors::ThrowIfPalmError (-1);
+ }
+
+ srcH = ::DmQueryRecord (dbP, i);
+
+ entry.localChunkID = offset;
+ entry.attributes = attr;
+ entry.uniqueID[0] = (uniqueID >> 16) & 0x00FF;
+ entry.uniqueID[1] = (uniqueID >> 8) & 0x00FF;
+ entry.uniqueID[2] = uniqueID & 0x00FF;
+
+ if (srcH)
+ offset += ::MemHandleSize (srcH);
+ }
+
+ // Clear out gap
+ if (kGapSize > 0)
+ memset (outP.Get() + (size - kGapSize), 0, kGapSize);
+
+ // Write out entry table
+ fh.PutBytes (outP.Get (), size);
+
+ // Write out the appInfo followed by sortInfo, if they exist
+ if (appInfoID && appInfoSize)
+ {
+ UInt32 srcP;
+ StMemory outP (appInfoSize);
+ srcP = (UInt32) ::MemHandleLock (appInfoH);
+ EmMem_memcpy ((void*) outP.Get(), srcP, appInfoSize);
+ ::MemPtrUnlock ((MemPtr) srcP);
+ fh.PutBytes (outP.Get (), appInfoSize);
+ }
+
+ if (sortInfoID && sortInfoSize)
+ {
+ UInt32 srcP;
+ StMemory outP (sortInfoSize);
+ srcP = (UInt32) ::MemHandleLock (sortInfoH);
+ EmMem_memcpy ((void*) outP.Get(), srcP, sortInfoSize);
+ ::MemPtrUnlock ((MemPtr) srcP);
+ fh.PutBytes (outP.Get (), sortInfoSize);
+ }
+
+ // Write out each record
+ for (i=0; i<numRecords; i++)
+ {
+ UInt32 recSize;
+
+ err = ::DmRecordInfo (dbP, i, &attr, &uniqueID, 0);
+ if (err)
+ {
+ Errors::ThrowIfPalmError (-1);
+ }
+
+ srcH = ::DmQueryRecord (dbP, i);
+
+ if (srcH)
+ {
+ UInt32 srcP;
+
+ recSize = ::MemHandleSize(srcH);
+ StMemory outP (recSize);
+ srcP = (UInt32) ::MemHandleLock (srcH);
+ EmMem_memcpy ((void*) outP.Get(), srcP, recSize);
+ ::MemPtrUnlock ((MemPtr) srcP);
+ fh.PutBytes (outP.Get (), recSize);
+ }
+ }
+ }
+
+ // Clean up
+ ::DmCloseDatabase (dbP);
+ }
+ catch (...)
+ {
+ if (dbP)
+ ::DmCloseDatabase (dbP);
+
+ throw;
+ }
+}
+
+
+// ---------------------------------------------------------------------------
+// ¥ SavePalmFile
+// ---------------------------------------------------------------------------
+// Saves a Palm OS program or database file to a file.
+
+void SavePalmFile (EmStreamFile& appFile, UInt16 cardNo, const char* databaseName)
+{
+ ::PrvMyShlExportAsPilotFile (appFile, cardNo, databaseName);
+}