1 /* 2 * Copyright 2003, Tyler Dauwalder, tyler@dauwalder.net. 3 * Distributed under the terms of the MIT License. 4 */ 5 6 7 #include "DString.h" 8 9 #include <string.h> 10 11 12 /*! \brief Creates a useless, empty string object. */ 13 DString::DString() 14 : 15 fLength(0), 16 fString(NULL) 17 { 18 } 19 20 21 /*! \brief Create a new DString object that is a copy of \a ref. */ 22 DString::DString(const DString &ref) 23 : 24 fLength(0), 25 fString(NULL) 26 { 27 SetTo(ref); 28 } 29 30 31 /*! \brief Creates a new DString \a fieldLength bytes long that contains 32 at most the first \c (fieldLength-1) bytes of \a string.Cs0(). 33 */ 34 DString::DString(const UdfString &string, uint8 fieldLength) 35 : 36 fLength(0), 37 fString(NULL) 38 { 39 SetTo(string, fieldLength); 40 } 41 42 43 /*! \brief Creates a new DString \a fieldLength bytes long that contains 44 at most the first \c (fieldLength-1) bytes of the Cs0 representation 45 of the NULL-terminated UTF8 string \a utf8. 46 */ 47 DString::DString(const char *utf8, uint8 fieldLength) 48 : 49 fLength(0), 50 fString(NULL) 51 { 52 SetTo(utf8, fieldLength); 53 } 54 55 56 DString::~DString() 57 { 58 delete[] fString; 59 } 60 61 62 void 63 DString::SetTo(const DString &ref) 64 { 65 _Clear(); 66 if (ref.Length() > 0) { 67 fString = new(nothrow) uint8[ref.Length()]; 68 if (fString != NULL) { 69 fLength = ref.Length(); 70 memcpy(fString, ref.String(), fLength); 71 } 72 } 73 } 74 75 76 /*! \brief Sets the DString be \a fieldLength bytes long and contain 77 at most the first \c (fieldLength-1) bytes of \a string.Cs0(). 78 */ 79 void 80 DString::SetTo(const UdfString &string, uint8 fieldLength) 81 { 82 _Clear(); 83 if (fieldLength > 0) { 84 // Allocate our string 85 fString = new(nothrow) uint8[fieldLength]; 86 status_t error = fString ? B_OK : B_NO_MEMORY; 87 if (!error) { 88 // Figure out how many bytes to copy 89 uint32 sourceLength = string.Cs0Length(); 90 if (sourceLength > 0) { 91 uint8 destLength = sourceLength > uint8(fieldLength - 1) 92 ? uint8(fieldLength - 1) : uint8(sourceLength); 93 // If the source string is 16-bit unicode, make sure any dangling 94 // half-character at the end of the string is not copied 95 if (string.Cs0()[1] == '\x10' && destLength > 0 96 && destLength % 2 == 0) 97 destLength--; 98 // Copy 99 memcpy(fString, string.Cs0(), destLength); 100 // Zero any characters between the end of the string and 101 // the terminating string length character 102 if (destLength < fieldLength - 1) 103 memset(&fString[destLength], 0, fieldLength - 1 - destLength); 104 // Write the string length to the last character in the field 105 fString[fieldLength - 1] = destLength; 106 } else { 107 // Empty strings are to contain all zeros 108 memset(fString, 0, fieldLength); 109 } 110 } 111 } 112 } 113 114 115 /*! \brief Sets the DString be \a fieldLength bytes long and contain 116 at most the first \c (fieldLength-1) bytes of the Cs0 representation 117 of the NULL-terminated UTF8 string \a utf8. 118 */ 119 void 120 DString::SetTo(const char *utf8, uint8 fieldLength) 121 { 122 UdfString string(utf8); 123 SetTo(string, fieldLength); 124 } 125 126 127 void 128 DString::_Clear() 129 { 130 DEBUG_INIT("DString"); 131 delete[] fString; 132 fString = NULL; 133 fLength = 0; 134 } 135