summaryrefslogtreecommitdiff
path: root/gptpart.cc
diff options
context:
space:
mode:
authorsrs5694 <srs5694@users.sourceforge.net>2010-01-28 21:10:52 -0500
committersrs5694 <srs5694@users.sourceforge.net>2010-01-28 21:10:52 -0500
commit0a6973119c9e9984ad47a6da3231e8d16f996c5c (patch)
tree456b81b56315eca6ac64688db34cbb0a25a87f41 /gptpart.cc
parent91544e13fb56ef339277a8f73f761ff004b2e74f (diff)
downloadsgdisk-0a6973119c9e9984ad47a6da3231e8d16f996c5c.tar.gz
Nearing 0.6.2 release; Windows version now works.
Diffstat (limited to 'gptpart.cc')
-rw-r--r--gptpart.cc213
1 files changed, 113 insertions, 100 deletions
diff --git a/gptpart.cc b/gptpart.cc
index c6504c1..29b2df9 100644
--- a/gptpart.cc
+++ b/gptpart.cc
@@ -35,17 +35,6 @@ GPTPart::GPTPart(void) {
GPTPart::~GPTPart(void) {
} // destructor
-// Return partition's name field, converted to a C++ ASCII string
-string GPTPart::GetName(void) {
- string theName;
- int i;
-
- for (i = 0; i < NAME_SIZE; i += 2) {
- theName += name[i];
- } // for
- return theName;
-} // GPTPart::GetName()
-
// Return the gdisk-specific two-byte hex code for the partition
uint16_t GPTPart::GetHexType(void) {
return typeHelper.GUIDToID(partitionType);
@@ -66,18 +55,30 @@ uint64_t GPTPart::GetLengthLBA(void) {
return length;
} // GPTPart::GetLengthLBA()
-GPTPart & GPTPart::operator=(const GPTPart & orig) {
+// Return partition's name field, converted to a C++ ASCII string
+string GPTPart::GetName(void) {
+ string theName;
int i;
- partitionType = orig.partitionType;
- uniqueGUID = orig.uniqueGUID;
- firstLBA = orig.firstLBA;
- lastLBA = orig.lastLBA;
- attributes = orig.attributes;
- for (i = 0; i < NAME_SIZE; i++)
- name[i] = orig.name[i];
- return *this;
-} // assignment operator
+ theName = "";
+ for (i = 0; i < NAME_SIZE; i += 2) {
+ if (name[i] != '\0')
+ theName += name[i];
+ } // for
+ return theName;
+} // GPTPart::GetName()
+
+// Set the type code to the specified one. Also changes the partition
+// name *IF* the current name is the generic one for the current partition
+// type.
+void GPTPart::SetType(struct GUIDData t) {
+ int nameSame = 1, currentLength, i;
+
+ if (GetName() == typeHelper.GUIDToName(partitionType)) {
+ SetName(typeHelper.GUIDToName(t));
+ } // if
+ partitionType = t;
+} // GPTPart::SetType()
// Sets the unique GUID to a value of 0 or a random value,
// depending on the parameter: 0 = 0, anything else = random
@@ -93,47 +94,54 @@ void GPTPart::SetUniqueGUID(int zeroOrRandom) {
}
} // GPTPart::SetUniqueGUID()
-// Blank (delete) a single partition
-void GPTPart::BlankPartition(void) {
- int j;
- GUIDData zeroGUID;
+// Set the name for a partition to theName, or prompt for a name if
+// theName is empty. Note that theName is a standard C++-style ASCII
+// string, although the GUID partition definition requires a UTF-16LE
+// string. This function creates a simple-minded copy for this.
+void GPTPart::SetName(const string & theName) {
+ char newName[NAME_SIZE]; // New name
+ char *junk;
+ int i;
- zeroGUID.data1 = 0;
- zeroGUID.data2 = 0;
- uniqueGUID = zeroGUID;
- partitionType = zeroGUID;
- firstLBA = 0;
- lastLBA = 0;
- attributes = 0;
- for (j = 0; j < NAME_SIZE; j++)
- name[j] = '\0';
-} // GPTPart::BlankPartition
+ // Blank out new name string, just to be on the safe side....
+ for (i = 0; i < NAME_SIZE; i++)
+ newName[i] = '\0';
-// Returns 1 if the two partitions overlap, 0 if they don't
-int GPTPart::DoTheyOverlap(GPTPart* other) {
- int theyDo = 0;
+ if (theName == "") { // No name specified, so get one from the user
+ cout << "Enter name: ";
+ junk = fgets(newName, NAME_SIZE / 2, stdin);
- // Don't bother checking unless these are defined (both start and end points
- // are 0 for undefined partitions, so just check the start points)
- if ((firstLBA != 0) && (other->firstLBA != 0)) {
- if ((firstLBA < other->lastLBA) && (lastLBA >= other->firstLBA))
- theyDo = 1;
- if ((other->firstLBA < lastLBA) && (other->lastLBA >= firstLBA))
- theyDo = 1;
+ // Input is likely to include a newline, so remove it....
+ i = strlen(newName);
+ if (newName[i - 1] == '\n')
+ newName[i - 1] = '\0';
+ } else {
+ strcpy(newName, theName.substr(0, NAME_SIZE / 2).c_str());
} // if
- return (theyDo);
-} // GPTPart::DoTheyOverlap()
-// Reverse the bytes of integral data types; used on big-endian systems.
-void GPTPart::ReversePartBytes(void) {
- ReverseBytes(&partitionType.data1, 8);
- ReverseBytes(&partitionType.data2, 8);
- ReverseBytes(&uniqueGUID.data1, 8);
- ReverseBytes(&uniqueGUID.data2, 8);
- ReverseBytes(&firstLBA, 8);
- ReverseBytes(&lastLBA, 8);
- ReverseBytes(&attributes, 8);
-} // GPTPart::ReverseBytes()
+ // Copy the C-style ASCII string from newName into a form that the GPT
+ // table will accept....
+ for (i = 0; i < NAME_SIZE; i++) {
+ if ((i % 2) == 0) {
+ name[i] = newName[(i / 2)];
+ } else {
+ name[i] = '\0';
+ } // if/else
+ } // for
+} // GPTPart::SetName()
+
+GPTPart & GPTPart::operator=(const GPTPart & orig) {
+ int i;
+
+ partitionType = orig.partitionType;
+ uniqueGUID = orig.uniqueGUID;
+ firstLBA = orig.firstLBA;
+ lastLBA = orig.lastLBA;
+ attributes = orig.attributes;
+ for (i = 0; i < NAME_SIZE; i++)
+ name[i] = orig.name[i];
+ return *this;
+} // assignment operator
// Display summary information; does nothing if the partition is empty.
void GPTPart::ShowSummary(int partNum, uint32_t blockSize) {
@@ -155,7 +163,7 @@ void GPTPart::ShowSummary(int partNum, uint32_t blockSize) {
cout.setf(ios::uppercase);
cout << hex << typeHelper.GUIDToID(partitionType) << " " << dec;
cout.fill(' ');
- cout.setf(ios::right);
+// cout.setf(ios::right);
cout << GetName().substr(0, 23) << "\n";
cout.fill(' ');
} // if
@@ -172,24 +180,65 @@ void GPTPart::ShowDetails(uint32_t blockSize) {
cout << "Partition unique GUID: " << GUIDToStr(uniqueGUID) << "\n";
cout << "First sector: " << firstLBA << " (at "
- << BytesToSI(firstLBA * blockSize) << ")\n";
+ << BytesToSI(firstLBA * blockSize) << ")\n";
cout << "Last sector: " << lastLBA << " (at "
- << BytesToSI(lastLBA * blockSize) << ")\n";
+ << BytesToSI(lastLBA * blockSize) << ")\n";
size = (lastLBA - firstLBA + 1);
cout << "Partition size: " << size << " sectors ("
- << BytesToSI(size * ((uint64_t) blockSize)) << ")\n";
+ << BytesToSI(size * ((uint64_t) blockSize)) << ")\n";
cout << "Attribute flags: ";
cout.fill('0');
cout.width(16);
- cout << right;
cout << hex;
cout << attributes << "\n";
- cout << left;
cout << dec;
cout << "Partition name: " << GetName() << "\n";
+ cout.fill(' ');
} // if
} // GPTPart::ShowDetails()
+// Blank (delete) a single partition
+void GPTPart::BlankPartition(void) {
+ int j;
+ GUIDData zeroGUID;
+
+ zeroGUID.data1 = 0;
+ zeroGUID.data2 = 0;
+ uniqueGUID = zeroGUID;
+ partitionType = zeroGUID;
+ firstLBA = 0;
+ lastLBA = 0;
+ attributes = 0;
+ for (j = 0; j < NAME_SIZE; j++)
+ name[j] = '\0';
+} // GPTPart::BlankPartition
+
+// Returns 1 if the two partitions overlap, 0 if they don't
+int GPTPart::DoTheyOverlap(const GPTPart & other) {
+ int theyDo = 0;
+
+ // Don't bother checking unless these are defined (both start and end points
+ // are 0 for undefined partitions, so just check the start points)
+ if ((firstLBA != 0) && (other.firstLBA != 0)) {
+ if ((firstLBA < other.lastLBA) && (lastLBA >= other.firstLBA))
+ theyDo = 1;
+ if ((other.firstLBA < lastLBA) && (other.lastLBA >= firstLBA))
+ theyDo = 1;
+ } // if
+ return (theyDo);
+} // GPTPart::DoTheyOverlap()
+
+// Reverse the bytes of integral data types; used on big-endian systems.
+void GPTPart::ReversePartBytes(void) {
+ ReverseBytes(&partitionType.data1, 8);
+ ReverseBytes(&partitionType.data2, 8);
+ ReverseBytes(&uniqueGUID.data1, 8);
+ ReverseBytes(&uniqueGUID.data2, 8);
+ ReverseBytes(&firstLBA, 8);
+ ReverseBytes(&lastLBA, 8);
+ ReverseBytes(&attributes, 8);
+} // GPTPart::ReverseBytes()
+
/****************************************
* Functions requiring user interaction *
****************************************/
@@ -216,46 +265,10 @@ void GPTPart::ChangeType(void) {
newType = typeHelper.IDToGUID((uint16_t) typeNum);
else // user wants to enter the GUID directly, so do that
newType = GetGUID();
- partitionType = newType;
+ SetType(newType);
cout << "Changed type of partition to '" << typeHelper.GUIDToName(partitionType) << "'\n";
} // GPTPart::ChangeType()
-// Set the name for a partition to theName, or prompt for a name if
-// theName is empty. Note that theName is a standard C++-style ASCII
-// string, although the GUID partition definition requires a UTF-16LE
-// string. This function creates a simple-minded copy for this.
-void GPTPart::SetName(string theName) {
- char newName[NAME_SIZE]; // New name
- char *junk;
- int i;
-
- // Blank out new name string, just to be on the safe side....
- for (i = 0; i < NAME_SIZE; i++)
- newName[i] = '\0';
-
- if (theName == "") { // No name specified, so get one from the user
- cout << "Enter name: ";
- junk = fgets(newName, NAME_SIZE / 2, stdin);
-
- // Input is likely to include a newline, so remove it....
- i = strlen(newName);
- if (newName[i - 1] == '\n')
- newName[i - 1] = '\0';
- } else {
- strcpy(newName, theName.substr(0, NAME_SIZE / 2).c_str());
- } // if
-
- // Copy the C-style ASCII string from newName into a form that the GPT
- // table will accept....
- for (i = 0; i < NAME_SIZE; i++) {
- if ((i % 2) == 0) {
- name[i] = newName[(i / 2)];
- } else {
- name[i] = '\0';
- } // if/else
- } // for
-} // GPTPart::SetName()
-
/***********************************
* Non-class but related functions *
***********************************/