home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1996 February: Tool Chest / Apple Developer CD Series Tool Chest February 1996 (Apple Computer)(1996).iso / Sample Code / AOCE Sample Code / PowerTalk Access Modules / Sample SMSAM / SampleSMSAM Source / BuildingBlocks / PascalString.cp < prev    next >
Encoding:
Text File  |  1995-07-28  |  17.5 KB  |  599 lines  |  [TEXT/KAHL]

  1. //----------------------------------------------------------------------------------------
  2. // PascalString.cp 
  3. // Copyright © 1985-1992 by Apple Computer, Inc.  All rights reserved.
  4. //----------------------------------------------------------------------------------------
  5.  
  6.  
  7. #include "PascalString.h"
  8.  
  9. #ifndef __STDIO__
  10. #include <StdIo.h>
  11. #endif
  12.  
  13. #ifndef __STRING__
  14. #include <String.h>
  15. #endif
  16.  
  17.  
  18. #pragma segment Main
  19.  
  20.  
  21. //========================================================================================
  22. // CLASS CString
  23. //========================================================================================
  24.  
  25.  
  26. //----------------------------------------------------------------------------------------
  27. // CString::InsertHelper(CString):
  28. //----------------------------------------------------------------------------------------
  29.  
  30. void CString::InsertHelper(const CString& insStr,
  31.                           short pos,
  32.                           short maxLength)
  33. {
  34.     if (pos > Length() + 1)
  35.     {
  36. #if qDebugMsg
  37.         fprintf(stderr, "###CString::InsertHelper: Insert position greater than length of CString.\n");
  38. #endif
  39.         if (Length() < maxLength)    
  40.             pos = Length() + 1;
  41.     }
  42.     
  43. #if qDebugMsg
  44.     if (Length() + insStr.Length() > maxLength)
  45.         fprintf(stderr, "### CString::InsertHelper: CString truncated during insert call.\n");    
  46. #endif
  47.  
  48.     short usableLengthOfInsertString;
  49.     short endPosOfInsertString;
  50.     short usableLengthOfShiftedString;
  51.     
  52.     if (pos + insStr.Length() > maxLength)
  53.         usableLengthOfInsertString = maxLength - pos + 1;
  54.     else
  55.         usableLengthOfInsertString = insStr.Length();
  56.     endPosOfInsertString = pos + usableLengthOfInsertString - 1;
  57.     
  58.     if ((endPosOfInsertString + 1) + (Length() - pos + 1) > maxLength)
  59.         usableLengthOfShiftedString = maxLength - endPosOfInsertString;
  60.     else
  61.         usableLengthOfShiftedString = Length() - pos + 1;
  62.         
  63.     memmove(&fStr[endPosOfInsertString + 1], &fStr[pos], usableLengthOfShiftedString);
  64.     memmove(&fStr[pos], &insStr.fStr[1], usableLengthOfInsertString);
  65.     Length() = usableLengthOfShiftedString + endPosOfInsertString;
  66. } // CString::InsertHelper(CString)
  67.  
  68.  
  69. //----------------------------------------------------------------------------------------
  70. // CString::InsertHelper(char*):
  71. //----------------------------------------------------------------------------------------
  72.  
  73. void CString::InsertHelper(const char* insStr,
  74.                           short pos,
  75.                           short maxLength)
  76. {
  77.     this->InsertHelper(CStr255(insStr), pos, maxLength);
  78. } // CString::InsertHelper(char*)
  79.  
  80.  
  81. //----------------------------------------------------------------------------------------
  82. // CString::operator[]: !!! we'd ideally like this method to be inlined but CFront doesn't
  83. // seem to want to inline it for us !!!
  84. //----------------------------------------------------------------------------------------
  85.  
  86. unsigned char& CString::operator[](short pos)
  87. {
  88.     return fStr[pos];
  89. } // CString::operator[] for non-const CString
  90.  
  91.  
  92. //----------------------------------------------------------------------------------------
  93. // CString::operator char*:
  94. //----------------------------------------------------------------------------------------
  95.  
  96. CString::operator char*() const
  97. {
  98.     const short kTempCStrings = 4;
  99.     static short currentCString = 0;
  100.     static char cStrings[kTempCStrings][kStr255Len+1];
  101.     
  102.     currentCString = (currentCString + 1) % kTempCStrings;
  103.     
  104.     strncpy(cStrings[currentCString], (char *) &fStr[1], Length());
  105.     cStrings[currentCString][Length()] = '\0';
  106.     
  107.     return cStrings[currentCString];
  108. } // CString::operator char*
  109.  
  110.  
  111. //----------------------------------------------------------------------------------------
  112. // CString::operator long:
  113. //----------------------------------------------------------------------------------------
  114.  
  115. CString::operator long() const
  116. {
  117.     // The following statement looks like it should work. Right?
  118.     //
  119.     //    return *((long *) &fStr[1]);
  120.     //
  121.     // Wrong, the C compiler generates a MOVE.L starting on a odd byte boundary for the
  122.     // preceding statement. This is illegal on the 68000. But its _NOT_ a bug, because
  123.     // according to the ANSI C reference manual, "A pointer to one type may be converted
  124.     // to a pointer to another type. The resulting pointer may cause an addressing
  125.     // exception if the subject pointer does not refer to an object suitably aligned in
  126.     // storage".
  127.     
  128.     long returnLong;
  129.     
  130.     memcpy(&returnLong, &fStr[1], sizeof(long));
  131.     return returnLong;
  132. } // CString::operator long
  133.  
  134.  
  135. //----------------------------------------------------------------------------------------
  136. // CString::Pos(char*):
  137. //----------------------------------------------------------------------------------------
  138.  
  139. unsigned char CString::Pos(const char* subStr, unsigned char startPos)
  140. {
  141.     char cStr[kStr255Len + 1];
  142.     char* ptr;
  143.     
  144.     memcpy(cStr, &fStr[1], Length());
  145.     cStr[Length()] = 0;
  146.     ptr = strstr(&cStr[startPos - 1], subStr);
  147.     return ptr != NULL ? (ptr - cStr) + 1 : 0;
  148. } // CString::Pos(char*)
  149.  
  150.  
  151. //----------------------------------------------------------------------------------------
  152. // CString::Pos(CString):
  153. //----------------------------------------------------------------------------------------
  154.  
  155. unsigned char CString::Pos(const CString& subStr, unsigned char startPos)
  156. {
  157.     char cStr[kStr255Len + 1];
  158.  
  159.     memcpy(cStr, &subStr.fStr[1], subStr.Length());
  160.     cStr[subStr.Length()] = 0;
  161.     return this->Pos(cStr, startPos);
  162. } // CString::Pos(CString)
  163.  
  164.  
  165.  
  166. //========================================================================================
  167. // CLASS CStr255
  168. //========================================================================================
  169.  
  170.  
  171. //----------------------------------------------------------------------------------------
  172. // CStr255::CStr255(char*):
  173. //----------------------------------------------------------------------------------------
  174.  
  175. CStr255::CStr255(const char* str)
  176. {
  177.     // Truncate the C CString to 255 bytes if necessary.
  178.  
  179.     Length() = str == NULL ? 0 : strlen(str);
  180.     
  181.     if (Length() > kStr255Len)
  182.         Length() = kStr255Len;
  183.     memcpy(&fStr[1], str, Length());
  184. } // CStr255::CStr255(char*)
  185.  
  186.  
  187. //----------------------------------------------------------------------------------------
  188. // CStr255::CStr255(long): Useful for converting OSType's into CStr255's.
  189. //----------------------------------------------------------------------------------------
  190.  
  191. CStr255::CStr255(const long id)
  192. {
  193.     Length() = 4;
  194.     memcpy(&fStr[1], &id, Length());
  195. } // CStr255::CStr255(long)
  196.  
  197.  
  198. //----------------------------------------------------------------------------------------
  199. // CStr255::Copy:
  200. //----------------------------------------------------------------------------------------
  201.  
  202. CStr255 CStr255::Copy(short pos, short length)
  203. {
  204.     CStr255 newString;
  205.     
  206.     length = length > Length() - pos + kLengthByte ? Length() - pos + kLengthByte : length;
  207.     
  208.     if (length > 0)
  209.     {
  210.         memcpy(&newString.fStr[1], &fStr[pos], length);
  211.         newString.Length() = length;
  212.     }
  213.     else
  214.         newString = "";
  215.         
  216.     return newString;
  217.     
  218. } // CStr255::Copy
  219.  
  220.  
  221. //----------------------------------------------------------------------------------------
  222. // CStr255::operator+:
  223. //----------------------------------------------------------------------------------------
  224.  
  225. CStr255 operator+(const CString& s1,
  226.                   const char* s2)
  227. {
  228.     CStr255 newStr;
  229.     short s2Len = s2 == NULL ? 0 : strlen((const char *) s2);
  230.  
  231.     if (s1.Length() + s2Len > kStr255Len)
  232.         newStr.Length() = kStr255Len;
  233.     else
  234.         newStr.Length() = s1.Length() + s2Len;
  235.         
  236.     memcpy(&newStr.fStr[1], &s1.fStr[1], s1.Length());
  237.     memcpy(&newStr.fStr[s1.Length() + kLengthByte], s2, newStr.Length() - s1.Length());
  238.  
  239.     return newStr;
  240. } // CStr255::operator+
  241.  
  242.  
  243. //----------------------------------------------------------------------------------------
  244. // CStr255::operator+(char*,CString):
  245. //----------------------------------------------------------------------------------------
  246.  
  247. CStr255 operator+(const char* s1,
  248.                   const CString& s2)
  249. {
  250.     CStr255 newStr;
  251.     short s1Len = s1 == NULL ? 0 : strlen((const char *) s1);
  252.  
  253.     if (s1Len + s2.Length() > kStr255Len)
  254.         newStr.Length() = kStr255Len;
  255.     else
  256.         newStr.Length() = s1Len + s2.Length();
  257.         
  258.     memcpy(&newStr.fStr[1], s1, s1Len);
  259.     memcpy(&newStr.fStr[s1Len + kLengthByte], s2.fStr + 1, newStr.Length() - s1Len);
  260.  
  261.     return newStr;
  262. } // CStr255::operator+(char*,CString)
  263.  
  264.  
  265. //----------------------------------------------------------------------------------------
  266. // CStr255::operator+(CString,CString):
  267. //----------------------------------------------------------------------------------------
  268.  
  269. CStr255 operator+(const CString& s1,
  270.                   const CString& s2)
  271. {
  272.     CStr255 newStr;
  273.  
  274.     if (s1.Length() + s2.Length() > kStr255Len)
  275.         newStr.Length() = kStr255Len;
  276.     else
  277.         newStr.Length() = s1.Length() + s2.Length();
  278.         
  279.     memcpy(&newStr.fStr[1], &s1.fStr[1], s1.Length());
  280.     memcpy(&newStr.fStr[s1.Length() + kLengthByte], s2.fStr + 1, newStr.Length() - s1.Length());
  281.  
  282.     return newStr;
  283. } // CStr255::operator+(CString,CString)
  284.  
  285.  
  286. //----------------------------------------------------------------------------------------
  287. // CStr255::operator +=(CString):  Concatinate a string
  288. //----------------------------------------------------------------------------------------
  289.  
  290. CStr255& CStr255::operator += (const CString& str)
  291. {
  292.     InsertHelper (str, Length() + 1, kStr255Len);
  293.     return *this;
  294. } // CStr255::operator +=(CString)
  295.  
  296.  
  297. //----------------------------------------------------------------------------------------
  298. // CStr255::operator +=(char*):  Concatinate a string
  299. //----------------------------------------------------------------------------------------
  300.  
  301. CStr255& CStr255::operator += (const char* str)
  302. {
  303.     InsertHelper (str, Length() + 1, kStr255Len);
  304.     return *this;
  305. } // CStr255::operator +=(char*)
  306.  
  307.  
  308. //----------------------------------------------------------------------------------------
  309. // CStr255::operator +=(char):  Concatinate a single character
  310. //----------------------------------------------------------------------------------------
  311.  
  312. CStr255& CStr255::operator += (const char ch)
  313. {
  314.     if (++Length() <= kStr255Len)
  315.         fStr[Length()] = ch;
  316.     else
  317.     {
  318.         --Length();
  319. #if qDebugMsg
  320.         fprintf(stderr, "###CStr255::operator+=: Concatenation produces CStr255 overflow.\n");
  321. #endif
  322.     }
  323.     
  324.     return *this;
  325. } // CStr255::operator +=(char)
  326.  
  327.  
  328. //----------------------------------------------------------------------------------------
  329. // CStr255::operator =:
  330. //----------------------------------------------------------------------------------------
  331.  
  332. CStr255& CStr255::operator = (const char* str)
  333. {
  334.     if (str)
  335.     {
  336.         // Truncate the C CString to 255 bytes if necessary.
  337.         register size_t itsSize = strlen(str);
  338.         if (itsSize > kStr255Len)
  339.             Length() = kStr255Len;
  340.         else
  341.             Length() = itsSize;
  342.  
  343.         memcpy(&fStr[1], str, Length());
  344.     }
  345.     else
  346.         Length() = 0;
  347.     
  348.     return *this;
  349. } // CStr255::operator =
  350.  
  351.  
  352.  
  353. //========================================================================================
  354. // CLASS CStr63
  355. //========================================================================================
  356.  
  357.  
  358. //----------------------------------------------------------------------------------------
  359. // CStr63::CStr63(char*):
  360. //----------------------------------------------------------------------------------------
  361.  
  362. CStr63::CStr63(const char* str)
  363. {
  364.     // Truncate the C CString to 63 bytes if necessary.
  365.  
  366.     Length() = str == NULL ? 0 : strlen((const char*)str);
  367.     if (Length() > kStr63Len)
  368.         Length() = kStr63Len;
  369.     memcpy(&fStr[1], str, Length());
  370. } // CStr63::CStr63(char*)
  371.  
  372.  
  373. //----------------------------------------------------------------------------------------
  374. // CStr63::CStr63(long):
  375. //----------------------------------------------------------------------------------------
  376.  
  377. CStr63::CStr63(const long id)
  378. {
  379.     Length() = 4;
  380.     memcpy(&fStr[1], &id, Length());
  381. } // CStr63::CStr63(long)
  382.  
  383.  
  384. //----------------------------------------------------------------------------------------
  385. // CStr63::Copy:
  386. //----------------------------------------------------------------------------------------
  387.  
  388. CStr63 CStr63::Copy(short pos, short length)
  389. {
  390.     CStr63 newString;
  391.     
  392.     length = length > Length() - pos + kLengthByte ? Length() - pos + kLengthByte : length;
  393.     
  394.     if (length > 0)
  395.     {
  396.         memcpy(&newString.fStr[1], &fStr[pos], length);
  397.         newString.Length() = length;
  398.     }
  399.     else
  400.         newString = "";
  401.         
  402.     return newString;
  403.     
  404. } // CStr63::Copy
  405.  
  406.  
  407. //----------------------------------------------------------------------------------------
  408. // CStr63::operator +=(CString):  Concatinate a string
  409. //----------------------------------------------------------------------------------------
  410.  
  411. CStr63& CStr63::operator += (const CString& str)
  412. {
  413.     InsertHelper (str, Length() + 1, kStr63Len);
  414.     return *this;
  415. } // CStr63::operator +=(CString)
  416.  
  417.  
  418. //----------------------------------------------------------------------------------------
  419. // CStr63::operator +=(char*):  Concatinate a string
  420. //----------------------------------------------------------------------------------------
  421.  
  422. CStr63& CStr63::operator += (const char* str)
  423. {
  424.     InsertHelper (str, Length() + 1, kStr63Len);
  425.     return *this;
  426. } // CStr63::operator +=(char*)
  427.  
  428.  
  429. //----------------------------------------------------------------------------------------
  430. // CStr63::operator +=(char):  Concatinate a single character
  431. //----------------------------------------------------------------------------------------
  432.  
  433. CStr63& CStr63::operator += (const char ch)
  434. {
  435.     if (++Length() <= kStr63Len)
  436.         fStr[Length()] = ch;
  437.     else
  438.     {
  439.         --Length();
  440. #if qDebugMsg
  441.         fprintf(stderr, "###CStr63::operator+=: Concatenation produces CStr63 overflow.\n");
  442. #endif
  443.     }
  444.     
  445.     return *this;
  446. } // CStr63::operator +=(char)
  447.  
  448.  
  449.  
  450. //========================================================================================
  451. // CLASS CStr32
  452. //========================================================================================
  453.  
  454.  
  455. //----------------------------------------------------------------------------------------
  456. // CStr32::CStr32(char*):
  457. //----------------------------------------------------------------------------------------
  458.  
  459. CStr32::CStr32(const char* str)
  460. {
  461.     // Truncate the C CString to 32 bytes if necessary.
  462.  
  463.     Length() = str == NULL ? 0 : strlen((const char*)str);
  464.     if (Length() > kStr32Len)
  465.         Length() = kStr32Len;
  466.     memcpy(&fStr[1], str, Length());
  467. } // CStr32::CStr32(char*)
  468.  
  469.  
  470. //----------------------------------------------------------------------------------------
  471. // CStr32::CStr32(long):
  472. //----------------------------------------------------------------------------------------
  473.  
  474. CStr32::CStr32(const long id)
  475. {
  476.     Length() = 4;
  477.     memcpy(&fStr[1], &id, Length());
  478. } // CStr32::CStr32(long)
  479.  
  480.  
  481. //----------------------------------------------------------------------------------------
  482. // CStr32::Copy:
  483. //----------------------------------------------------------------------------------------
  484.  
  485. CStr32 CStr32::Copy(short pos, short length)
  486. {
  487.     CStr32 newString;
  488.     
  489.     length = length > Length() - pos + kLengthByte ? Length() - pos + kLengthByte : length;
  490.     
  491.     if (length > 0)
  492.     {
  493.         memcpy(&newString.fStr[1], &fStr[pos], length);
  494.         newString.Length() = length;
  495.     }
  496.     else
  497.         newString = "";
  498.         
  499.     return newString;
  500.  
  501. } // CStr32::Copy
  502.  
  503.  
  504.  
  505. //========================================================================================
  506. // CLASS CStr31
  507. //========================================================================================
  508.  
  509.  
  510. //----------------------------------------------------------------------------------------
  511. // CStr31::CStr31(char*):
  512. //----------------------------------------------------------------------------------------
  513.  
  514. CStr31::CStr31(const char* str)
  515. {
  516.     // Truncate the C CString to 31 bytes if necessary.
  517.  
  518.     Length() = str == NULL ? 0 : strlen((const char*)str);
  519.     if (Length() > kStr31Len)
  520.         Length() = kStr31Len;
  521.     memcpy(&fStr[1], str, Length());
  522. } // CStr31::CStr31(char*)
  523.  
  524.  
  525. //----------------------------------------------------------------------------------------
  526. // CStr31::CStr31(long):
  527. //----------------------------------------------------------------------------------------
  528.  
  529. CStr31::CStr31(const long id)
  530. {
  531.     Length() = 4;
  532.     memcpy(&fStr[1], &id, Length());
  533. } // CStr31::CStr31(long)
  534.  
  535.  
  536. //----------------------------------------------------------------------------------------
  537. // CStr31::Copy:
  538. //----------------------------------------------------------------------------------------
  539.  
  540. CStr31 CStr31::Copy(short pos, short length)
  541. {
  542.     CStr31 newString;
  543.     
  544.     length = length > Length() - pos + kLengthByte ? Length() - pos + kLengthByte : length;
  545.     
  546.     if (length > 0)
  547.     {
  548.         memcpy(&newString.fStr[1], &fStr[pos], length);
  549.         newString.Length() = length;
  550.     }
  551.     else
  552.         newString = "";
  553.         
  554.     return newString;
  555.  
  556. } // CStr31::Copy
  557.  
  558.  
  559. //----------------------------------------------------------------------------------------
  560. // CStr31::operator +=(CString):  Concatinate a string
  561. //----------------------------------------------------------------------------------------
  562.  
  563. CStr31& CStr31::operator += (const CString& str)
  564. {
  565.     InsertHelper (str, Length() + 1, kStr31Len);
  566.     return *this;
  567. } // CStr31::operator +=(CString)
  568.  
  569.  
  570. //----------------------------------------------------------------------------------------
  571. // CStr31::operator +=(char*):  Concatinate a string
  572. //----------------------------------------------------------------------------------------
  573.  
  574. CStr31& CStr31::operator += (const char* str)
  575. {
  576.     InsertHelper (str, Length() + 1, kStr31Len);
  577.     return *this;
  578. } // CStr31::operator +=(char*)
  579.  
  580.  
  581. //----------------------------------------------------------------------------------------
  582. // CStr31::operator +=(char):  Concatinate a single character
  583. //----------------------------------------------------------------------------------------
  584.  
  585. CStr31& CStr31::operator += (const char ch)
  586. {
  587.     if (++Length() <= kStr31Len)
  588.         fStr[Length()] = ch;
  589.     else
  590.     {
  591.         --Length();
  592. #if qDebugMsg
  593.         fprintf(stderr,"###CStr31::operator+=: Concatenation produces CStr31 overflow.\n");
  594. #endif
  595.     }
  596.     
  597.     return *this;
  598. } // CStr31::operator +=(char)
  599.