Hello folks,

I am still trying to figure out how exactly to receive whole databases beamed 
to my application... I think I've almost got it, but there is something still 
eluding me... Here is the problem.

1) On sysAppLaunchCmdSystemReset and sysAppLaunchCmdSyncNotify my application 
registers to receive databases with a particular extension:

    ExgRegisterData (appCreatorID, exgRegExtensionID, "DEF");

Here appCreatorID is the creator ID for my application and has been #defined 
elsewhere. My application checks the PalmOS version elsewhere and refuses to 
run under anything less than 3.0, so I don't need to check the OS version here.

2) On sysAppLaunchCmdExgReceiveData I try to receive the database:

Err ReceiveDatabase (ExgSocketPtr exgSocket)
{
    LocalID dbID;
    Boolean doReset;
    Err err;

    err = ExgAccept (exgSocket);
    if (err == errNone)
        err = ExgDBRead (ReadDBData, DeleteProc, exgSocket, &dbID, 0, &doReset, 
true);
    return err;
}

For the purpose of the exercise, ignore that I am not resetting the device, if 
necessary, and that I am not checking whether the application is running; the 
database in question is closed most of the time and when it is not, the 
application is busy doing some work and won't accept any beaming (or any other) 
events anyway.

3) The callback function ReadDBData is pretty straightforward:

Err ReadDBData (void *dataP, UInt32 *sizeP, void *userDataP)
{
    Err err;

    *sizeP = ExgReceive ((ExgSocketPtr) userDataP, dataP, *sizeP, &err);
    return err;
}

4) The problem is with the callback function DeleteProc. If the database that 
is being beamed to the application already exists, I want the application to 
examine a particular record that contains the database creation timestamp and, 
before deleting the existing database, to ask the user for permission, if the 
local database is newer than the one that is being beamed to the application. 
When sending the database, I stuff the creation timestamp in the appData field 
of the ExgSocketType structure. Here is how I'm trying to achieve this:

Boolean DeleteProc (const Char *nameP, UInt16 version, UInt16 cardNo, LocalID 
dbID, void *userData)
{
    DmOpenRef dbRef;
    DateTimeType timeStampLocal, timeStampRemote;
    UInt32 appData;
    ExgSocketPtr socketP;

    dbRef = DmOpenDatabase (cardNo, dbID, dmModeReadOnly);
    if (dbRef == NULL)
        return false;
    GetDBTimeStamp (dbRef, &timeStampLocal);
    if (DmCloseDatabase (dbRef) != errNone)
        return false;
    socketP = (ExgSocketPtr) userData;
    appData = socketP->appData;
    if (TimDateTimeToSeconds (&timeStampLocal) > appData)
    {
        if (FrmAlert (kOldDatabaseAlert) != kOldDatabaseAlertYesButton)
            return false;
    }
    return (DmDeleteDatabase (cardNo, dbID) == errNone);
}

Here the function GetDBTimeStamp fetches the timestamp from the local database. 
It works correctly - I have verified this with a debugger.

On the sending side, I do

Err BeamDatabase (void)
{
    ExgSocketType exgSocket;
    Err err = errNone;
    LocalID dbID;
    DmOpenRef dbRef;
    DateTimeType timeStampLocal;

    dbID = DmFindDatabase (0, "DATABASE.DEF");
    if (dbID)
    {
        MemSet (&exgSocket, sizeof (exgSocket), 0);
        exgSocket.name = "DATABASE.DEF";
        exgSocket.description = "DATABASE.DEF";
        dbRef = DmOpenDatabase (0, dbID, dmModeReadOnly);
        if (dbRef == NULL)
            return DmGetLastErr ();
        GetDBTimeStamp (dbRef, &timeStampLocal);
        if (DmCloseDatabase (dbRef) != errNone)
            return DmGetLastErr ();
        exgSocket.appData = TimDateTimeToSeconds (&timeStampLocal);
        exgSocket.target = GetCreatorID ();
        err = ExgPut (&exgSocket);
        if (! err)
            err = ExgDisconnect (&exgSocket, ExgDBWrite (WriteDBData, 
&exgSocket, exgSocket.name, dbID, 0));
    }
    else
        err = DmGetLastErr ();
    return err;
}

where the function WriteDBData is again straightforward:

Err WriteDBData (const void *dataP, UInt32 *sizeP, void *userDataP)
{
    Err err;
  
    *sizeP = ExgSend ((ExgSocketPtr) userDataP, dataP, *sizeP, &err);
    return err;
}

Again, I have verified with a debugger that the appData field is set correctly 
before calling ExgPut.

Well, folks, the problem is that on the receiving end (in the function 
DeleteProc), the value of appData is zero. :-( Somehow, it gets lost in the 
transmission and the whole check fails.

Any idea what might be going wrong?

Regards,
Vesselin
-- 
For information on using the Palm Developer Forums, or to unsubscribe, please 
see http://www.palmos.com/dev/support/forums/

Reply via email to