home *** CD-ROM | disk | FTP | other *** search
/ linuxmafia.com 2016 / linuxmafia.com.tar / linuxmafia.com / pub / palmos / wapuniverse-src-0.3.5.build9.tar.gz / wapuniverse-src-0.3.5.build9.tar / wapuniverse-0.3.5.build9 / dbUrl.c < prev    next >
C/C++ Source or Header  |  2000-11-12  |  13KB  |  409 lines

  1. //---------------------------------------------------------------------------
  2. // dbUrl.c
  3. // Contains PalmOS specific Database code
  4. //
  5. // Project: WAPUniverse for PalmOS
  6. // Copyright ⌐ 1999-2000 Filip Onkelinx
  7. //
  8. // http://www.wapuniverse.com/
  9. // filip@onkelinx.com
  10. //
  11. // This program is free software; you can redistribute it and/or
  12. // modify it under the terms of the GNU General Public License
  13. // as published by the Free Software Foundation; either version 2
  14. // of the License, or (at your option) any later version.
  15. //
  16. // This program is distributed in the hope that it will be useful,
  17. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  18. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  19. // GNU General Public License for more details.
  20. //
  21. // You should have received a copy of the GNU General Public License
  22. // along with this program; if not, write to the Free Software 
  23. // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 
  24. //
  25. //
  26. // $Workfile: dbUrl.c $  
  27. // $Author: wapuniverse $  
  28. // $Date: 2000/11/11 20:51:09 $     
  29. // $Revision: 1.7 $
  30. //
  31. // $Header: /cvsroot/wapuniverse/wapuniverse/src/dbUrl.c,v 1.7 2000/11/11 20:51:09 wapuniverse Exp $
  32. //
  33. //---------------------------------------------------------------------------
  34. #include    <PalmOS.h>
  35. #include    <SysEvtMgr.h>
  36. #include    "WAPUniverse.h"
  37. #include    "../res/WAPUniverse_res.h"
  38. #include    "dbUrl.h"
  39.  
  40. Boolean dbUrlCreateRecord (GlobalsType *g)
  41. {
  42.   MemPtr          p;
  43.   MemHandle       urlRec;
  44.   UInt16          index = 0;
  45.   Err             error;
  46.   UInt16          attr;         // record attributes (category)
  47.  
  48.   // Create a new first record in the database
  49.   urlRec = DmNewRecord (g->DbUrlDb, &index, dbUrlNewURLSize);
  50.  
  51.   // Lock down the block containing the new record.
  52.   p = MemHandleLock (urlRec);
  53.  
  54.   // Write a zero to the first byte of the record to null terminate the new
  55.   // URL string.
  56.   error = DmSet (p, 0, dbUrlNewURLSize, (UInt8) 0);
  57.  
  58.   // Check for fatal error.
  59.   ErrFatalDisplayIf (error, "Could not write to new record.");
  60.  
  61.   // Unlock the block of the new record.
  62.   MemPtrUnlock (p);
  63.  
  64.  
  65.   // P11. Set the category of the new record to the current category.
  66.   DmRecordInfo (g->DbUrlDb, index, &attr, NULL, NULL);
  67.   attr &= ~dmRecAttrCategoryMask; // Remove all category bits
  68.   if (g->DbUrlCurrentCategory == dmAllCategories)
  69.     {
  70.       // Since the user isn't looking in any particular category place
  71.       // the new record in the unfiled category.
  72.       attr |= dmUnfiledCategory;
  73.     }
  74.   else
  75.     {
  76.       // Set the attribute bits to indicate the current category.
  77.       attr |= g->DbUrlCurrentCategory;
  78.     }
  79.   DmSetRecordInfo (g->DbUrlDb, index, &attr, NULL);
  80.  
  81.  
  82.   // Release the record to the database manager.  The true value indicates
  83.   // that
  84.   // the record contains "dirty" data.  Release Record will set the record's 
  85.   // dirty flag and update the database modification count.
  86.   DmReleaseRecord (g->DbUrlDb, index, true);
  87.  
  88.   // Remember the index of the current record.
  89.   g->DbUrlCurrentRecord = 0;
  90.   return (true);
  91. }
  92.  
  93. /************************************************************
  94.  *  FUNCTION: PackURL
  95.  *  DESCRIPTION: Packs a URL to consume less space in the DB
  96.  *  PARAMETERS: the unpacked URL (url), and the destination DB handle
  97.  *  RETURNS: no nothing, but it wouldn't hurt todo so ... 
  98.  *************************************************************/
  99. void dbUrlPackURL (dbUrlURL * url, MemHandle urlDBEntry)
  100. {
  101.   // figure out necessary size
  102.   UInt16            length = 0;
  103.   Char              *s;
  104.   UInt16            offset = 0;
  105.  
  106.   length = StrLen (url->name) + StrLen(url->urlstr)
  107.             + StrLen (url->connection) + 3; // 3 for 3 string terminators
  108.  
  109.   // resize the MemHandle
  110.   if (MemHandleResize (urlDBEntry, length) == 0)
  111.     {
  112.       // copy the fields
  113.       s = MemHandleLock (urlDBEntry);
  114.       offset = 0;
  115.       DmStrCopy (s, offset, (Char *) url->name);
  116.       offset += StrLen (url->name) + 1;
  117.       DmStrCopy (s, offset, (Char *) url->urlstr);
  118.       offset += StrLen (url->urlstr) + 1;
  119.       DmStrCopy (s, offset, (Char *) url->connection);
  120.       MemHandleUnlock (urlDBEntry);
  121.     }
  122.     else
  123.     {
  124.             ErrDisplay ("***MemHandleResize Failed");
  125.     }
  126. }
  127.  
  128. /************************************************************
  129.  *  FUNCTION: 
  130.  *  DESCRIPTION: 
  131.  *  PARAMETERS: 
  132.  *  RETURNS: 
  133.  *************************************************************/
  134. void dbUrlUnPackURL (dbUrlURL * url, dbUrlPackedURL * packedURL)
  135. {
  136.   char*           s = packedURL->name;
  137.  
  138.   StrCopy (url->name, s);
  139.   s += StrLen (s) + 1;
  140.   StrCopy (url->urlstr, s);
  141.   s += StrLen (s) + 1;
  142.   StrCopy (url->connection, s);
  143.  
  144. }
  145.  
  146. /************************************************************
  147.  *  FUNCTION: 
  148.  *  DESCRIPTION: 
  149.  *  PARAMETERS: 
  150.  *  RETURNS: 
  151.  *************************************************************/
  152. void dbUrlOpenOrCreateDB(UInt16 mode, GlobalsType *g)
  153. {
  154.   Int16             error;        // error code
  155.   UInt16            cardNo;       // card containing the application database
  156.   LocalID         dbID;         // handle for application database
  157.   UInt16            dbAttrs;      // database attributes
  158.   MemHandle        currec;
  159.  
  160.   // Find the application's URL database.
  161.   g->DbUrlDb = DmOpenDatabaseByTypeCreator (dbUrlDBType, wuAppType, mode);
  162.   if (!g->DbUrlDb)
  163.     {
  164.       // The database doesn't exist, create it now.
  165.       error = DmCreateDatabase (0, dbUrlDBName, wuAppType,
  166.                                 dbUrlDBType, false);
  167.  
  168.       // Check for fatal error.
  169.       ErrFatalDisplayIf (error, "Could not create new DB.");
  170.  
  171.       // Find the application's database.
  172.       g->DbUrlDb = DmOpenDatabaseByTypeCreator (dbUrlDBType, wuAppType, mode);
  173.  
  174.       // Get info about the database
  175.       error = DmOpenDatabaseInfo (g->DbUrlDb, &dbID, NULL, NULL, &cardNo, NULL);
  176.  
  177.       // Check for fatal error.
  178.       ErrFatalDisplayIf (error, "Could not get DB info.");
  179.  
  180.       // Get attributes for the database
  181.       error = DmDatabaseInfo (0, dbID, NULL, &dbAttrs, NULL, NULL, NULL,
  182.                               NULL, NULL, NULL, NULL, NULL, NULL);
  183.  
  184.       // Check for fatal error.
  185.       ErrFatalDisplayIf (error, "Could not get DB info.");
  186.  
  187.       // Set the new attributes in the database
  188.       error = DmSetDatabaseInfo (0, dbID, NULL, &dbAttrs, NULL, NULL,
  189.                                  NULL, NULL, NULL, NULL, NULL, NULL, NULL);
  190.  
  191.       // Check for fatal error.
  192.       ErrFatalDisplayIf (error, "Could not set DB info.");
  193.  
  194.       // Store category info in the application's information block.
  195.       dbUrlInitAppInfo (g->DbUrlDb,g);
  196.  
  197.       // Create a default record for "WAPUniverse Home"
  198.       dbUrlCreateRecord (g);
  199.       StrCopy (g->DbUrlCurrentURL.name, "WAPUniverse Home");
  200.       StrCopy (g->DbUrlCurrentURL.urlstr, "http://www.wapuniverse.com/index.wml");
  201.       StrCopy (g->DbUrlCurrentURL.connection, "Ericsson");
  202.       currec = DmGetRecord (g->DbUrlDb, 0);
  203.       dbUrlPackURL (&g->DbUrlCurrentURL, currec);
  204.       DmReleaseRecord (g->DbUrlDb, 0, true);
  205.     }
  206.  
  207.   // Set current database record to no current record.
  208.   g->DbUrlCurrentRecord = noRecordSelected;
  209.  
  210.   // Get the name of the current category from the app info block.
  211.   // The app info block was created and initialized by MemoPadInitAppInfo.
  212.   // CategoryCreateList(g->DbUrlDb,CategoryName,g->DbUrlCurrentCategory,true,true,1,0,true);
  213.  
  214.   CategoryGetName (g->DbUrlDb, g->DbUrlCurrentCategory, g->DbUrlCategoryName);
  215.  
  216. }
  217.  
  218.  
  219. /************************************************************
  220.  *  FUNCTION: 
  221.  *  DESCRIPTION: 
  222.  *  PARAMETERS: 
  223.  *  RETURNS: 
  224.  *************************************************************/
  225. static Int16 dbUrlCompareRecords (dbUrlURLPtr u1, dbUrlURLPtr u2)
  226. {
  227.   return (StrCompare ((Char *) & u1->name, (Char *) & u2->name));
  228. }
  229.  
  230. void dbUrlReadCurrentUrl (GlobalsType *g)
  231. {
  232.   dbUrlPackedURL*    purl;
  233.   MemHandle            rechand;
  234.   Int16             seekAmount = g->DbUrlCurrentRecord;
  235.   UInt16            index = 0;
  236.  
  237.   // must do seek to skip over secret records
  238.   DmSeekRecordInCategory (g->DbUrlDb, &index, seekAmount, dmSeekForward, g->DbUrlCurrentCategory);
  239.   rechand = DmQueryRecord (g->DbUrlDb, index);
  240.   if (rechand)
  241.     {
  242.       purl = MemHandleLock (rechand);
  243.       dbUrlUnPackURL (&(g->DbUrlCurrentURL), purl);
  244.       MemHandleUnlock (rechand);
  245.     }
  246.  
  247. }
  248.  
  249. /************************************************************
  250.  *  FUNCTION: 
  251.  *  DESCRIPTION: 
  252.  *  PARAMETERS: 
  253.  *  RETURNS: 
  254.  *************************************************************/
  255. Err dbUrlSortRecord (DmOpenRef dbP, UInt16 *indexP)
  256. {
  257.   Err             err;
  258.   UInt16            index;
  259.   UInt16            attributes;
  260.   UInt32           uniqueID;
  261.   MemHandle          recordH;
  262.   MemHandle        h;
  263.   Boolean         dontMove;
  264.   dbUrlURLPtr          cmp;
  265.   dbUrlURLPtr          recordP;
  266.  
  267.   // Check if the record is already in the correct position.
  268.   recordP = MemHandleLock (DmQueryRecord (dbP, *indexP));
  269.   if (*indexP > 0)
  270.     {
  271.       // This record wasn't deleted and deleted records are at the end of the
  272.       // database so the prior record may not be deleted!
  273.       h = DmQueryRecord (dbP, *indexP - 1);
  274.       if (!h)
  275.         dontMove = false;
  276.       else
  277.         {
  278.           cmp = MemHandleLock (h);
  279.           dontMove = (dbUrlCompareRecords (cmp, recordP) == -1);
  280.           MemPtrUnlock (cmp);
  281.         }
  282.     }
  283.   else
  284.     dontMove = true;
  285.  
  286.   if (dontMove && (*indexP + 1 < DmNumRecords (dbP)))
  287.     {
  288.       DmRecordInfo (dbP, *indexP + 1, &attributes, NULL, NULL);
  289.       if (!(attributes & dmRecAttrDelete))
  290.         {
  291.           cmp = MemHandleLock (DmQueryRecord (dbP, *indexP + 1));
  292.           dontMove &= (dbUrlCompareRecords (recordP, cmp) == -1);
  293.           MemPtrUnlock (cmp);
  294.         }
  295.     }
  296.   MemPtrUnlock (recordP);
  297.  
  298.   if (dontMove)
  299.     return (0);
  300.  
  301.  
  302.   // Since the routine that determines the records sort position uses a 
  303.   // binary search algorythm we need to remove the record from the database 
  304.   // before we can determine its new position.  We will also save and restore 
  305.   // the 
  306.   // record's attributes and unique ID.
  307.   DmRecordInfo (dbP, *indexP, &attributes, &uniqueID, NULL);
  308.  
  309.   err = DmDetachRecord (dbP, *indexP, &recordH);
  310.   if (err)
  311.     return (err);
  312.  
  313.   recordP = MemHandleLock ((MemHandle) recordH);
  314.   index = DmFindSortPosition (dbP, recordP, NULL, (DmComparF *)
  315.                               dbUrlCompareRecords, 0);
  316.   MemPtrUnlock (recordP);
  317.  
  318.   err = DmAttachRecord (dbP, &index, recordH, 0);
  319.   if (err)
  320.     return (err);
  321.  
  322.   DmSetRecordInfo (dbP, index, &attributes, &uniqueID);
  323.  
  324.   *indexP = index;
  325.  
  326.   return (err);
  327. }
  328.  
  329. UInt16 dbUrlNumRecords(GlobalsType *g)
  330. {
  331.   return(DmNumRecordsInCategory (g->DbUrlDb, g->DbUrlCurrentCategory));
  332. }
  333.  
  334. Boolean dbUrlDeleteCurrentRecord (GlobalsType *g)
  335. {
  336.   Int16             seekAmount = g->DbUrlCurrentRecord;
  337.   UInt16            index = 0;
  338.  
  339.   DmSeekRecordInCategory (g->DbUrlDb, &index, seekAmount, dmSeekForward, dmAllCategories);
  340.   DmRemoveRecord (g->DbUrlDb, index);
  341.   return (true);
  342. }
  343.  
  344.  
  345.  
  346.  
  347. /************************************************************
  348.  *  FUNCTION: gWAPInitAppInfo
  349.  *  DESCRIPTION: Create an app info chunk if missing.  Set
  350.  *      the category strings to a default.
  351.  *  PARAMETERS: database poInt16er
  352.  *  RETURNS: 0 if successful, errorcode if not
  353.  *************************************************************/
  354. Err
  355. dbUrlInitAppInfo (DmOpenRef dbP, GlobalsType *g)
  356. {
  357.   UInt16            cardNo;
  358.   MemHandle        h;
  359.   LocalID         dbID;
  360.   LocalID         appInfoID;
  361.   gWAPAppInfoPtr  appInfoP;
  362.   gWAPAppInfoPtr  nilP = 0;
  363.  
  364.  
  365.   // We have a DmOpenRef and we want the database's app info block ID.
  366.   // Get the database's dbID and cardNo and then use them to get the
  367.   // appInfoID.
  368.   if (DmOpenDatabaseInfo (dbP, &dbID, NULL, NULL, &cardNo, NULL))
  369.     return dmErrInvalidParam;
  370.   if (DmDatabaseInfo (cardNo, dbID, NULL, NULL, NULL, NULL, NULL,
  371.                       NULL, NULL, &appInfoID, NULL, NULL, NULL))
  372.     return dmErrInvalidParam;
  373.  
  374.  
  375.   // If no appInfoID exists then we must create a new one.    
  376.   if (appInfoID == NULL)
  377.     {
  378.       h = DmNewHandle (dbP, sizeof (gWAPAppInfoType));
  379.       if (!h)
  380.         return dmErrMemError;
  381.  
  382.       appInfoID = MemHandleToLocalID (h);
  383.       DmSetDatabaseInfo (cardNo, dbID, NULL, NULL, NULL, NULL, NULL, NULL,
  384.                          NULL, &appInfoID, NULL, NULL, NULL);
  385.     }
  386.  
  387.  
  388.   // Lock the appInfoID and copy in defaults from our default structure.  
  389.   appInfoP = MemLocalIDToLockedPtr (appInfoID, cardNo);
  390.  
  391.   // Clear the app info block.
  392.   // DmSet (appInfoP, 0, sizeof (gWAPAppInfoType), 0);
  393.   DmWrite (appInfoP, 0, &(g->WAPAppInfo), sizeof (gWAPAppInfoType));
  394.  
  395.   // Initialize the categories.
  396.   CategoryInitialize ((AppInfoPtr) appInfoP, localizedAppInfoStr);
  397.  
  398.   // Initialize reserved2.  This is actually redundant since the DmSet
  399.   // call above has already set reserved2 to zero.  But this shows how
  400.   // to set variables in addition to the categories.
  401.   DmSet (appInfoP, (UInt32) & nilP->reserved2, sizeof
  402.          (appInfoP->reserved2), 0);
  403.  
  404.   MemPtrUnlock (appInfoP);
  405.   return 0;
  406. }
  407.  
  408.  
  409.