1 /*****************************************************************************\
3 * Name : version structures: version, version_record *
4 * Author : Chris Koeritz *
6 *******************************************************************************
7 * Copyright (c) 1996-$now By Author. This program is free software; you can *
8 * redistribute it and/or modify it under the terms of the GNU General Public *
9 * License as published by the Free Software Foundation; either version 2 of *
10 * the License or (at your option) any later version. This is online at: *
11 * http://www.fsf.org/copyleft/gpl.html *
12 * Please send any updates to: fred@gruntose.com *
13 \*****************************************************************************/
15 #include "string_array.h"
16 #include "version_record.h"
18 #include <basis/functions.h>
22 using namespace basis;
24 namespace structures {
26 void *version::__global_module_handle()
28 static void *__mod_hand = 0;
33 : _components(new string_array)
35 set_component(MAJOR, "0");
36 set_component(MINOR, "0");
37 set_component(REVISION, "0");
38 set_component(BUILD, "0");
41 version::version(const string_array &version_info)
42 : _components(new string_array(version_info))
44 for (int i = 0; i < _components->length(); i++) {
45 if (!(*_components)[i]) {
46 // this component is blank; replace it with a zero.
47 (*_components)[i] = "0";
52 version::version(const astring &formatted_string)
53 : _components(new string_array)
55 astring verstring = formatted_string;
56 // scan through and replace bogus bits with reasonable bits.
57 for (int j = 0; j < verstring.length(); j++) {
58 if (verstring[j] == ',') verstring[j] = '.';
59 // replace commas with periods.
61 // locate the pieces of the version string.
62 for (int i = 0; i < verstring.length(); i++) {
63 int perindy = verstring.find('.', i);
64 if (negative(perindy)) {
65 if (verstring.length() - i > 0) {
66 // add any extra bits after the last period in the string.
67 *_components += verstring.substring(i, verstring.end());
71 // we found a period, so include anything between the current position and
72 // that as a component.
73 *_components += verstring.substring(i, perindy - 1);
75 // set i to be at the next period; it will be incremented past that.
79 version::version(int maj, int min, int rev, int build)
80 : _components(new string_array)
82 *this = version(a_sprintf("%u.%u.%u.%u", basis::un_int(maj), basis::un_int(min), basis::un_int(rev),
83 basis::un_int(build)));
86 version::version(const version &to_copy)
87 : _components(new string_array)
90 version::~version() { WHACK(_components); }
92 version &version::operator =(const version &to_copy)
94 if (this != &to_copy) *_components = *to_copy._components;
98 astring version::text_form() const { return flex_text_form(); }
100 int version::components() const { return _components->length(); }
102 int version::v_major() const
103 { return int(get_component(MAJOR).convert(0)); }
105 int version::v_minor() const
106 { return int(get_component(MINOR).convert(0)); }
108 int version::v_revision() const
109 { return int(get_component(REVISION).convert(0)); }
111 int version::v_build() const
112 { return int(get_component(BUILD).convert(0)); }
114 astring version::get_component(int index) const
116 bounds_return(index, 0, _components->length() - 1, "0");
117 return (*_components)[index];
120 void version::set_component(int index, const astring &to_set)
122 if (_components->length() <= index)
123 _components->resize(index + 1);
125 (*_components)[index] = to_set;
127 (*_components)[index] = "0";
130 bool version::equal_to(const equalizable &to_test) const
132 const version *cast = cast_or_throw(to_test, *this);
133 return *_components == *cast->_components;
136 bool version::less_than(const orderable &to_test) const
138 const version *cast = cast_or_throw(to_test, *this);
139 if (v_major() < cast->v_major()) return true;
140 else if (v_major() > cast->v_major()) return false;
141 if (v_minor() < cast->v_minor()) return true;
142 else if (v_minor() > cast->v_minor()) return false;
143 if (v_revision() < cast->v_revision()) return true;
144 else if (v_revision() > cast->v_revision()) return false;
145 if (v_build() < cast->v_build()) return true;
149 bool version::compatible(const version &to_test) const
151 //fix to be more general
152 return (v_major() == to_test.v_major())
153 && (v_minor() == to_test.v_minor())
154 && (v_revision() == to_test.v_revision());
157 bool version::bogus() const
158 { return !v_major() && !v_minor() && !v_revision() && !v_build(); }
161 if (style != DOTS) to_return += ", "; \
162 else to_return += "."
164 astring version::flex_text_form(version_style style, int where) const
166 // note: the conversions below are to ensure proper treatment of the
167 // size of the int16 types by win32.
170 if (style == DETAILED) to_return += "major ";
171 astring temp = get_component(MAJOR);
172 if (!temp) temp = "0";
174 if (where == MAJOR) return to_return;
177 if (style == DETAILED) to_return += "minor ";
178 temp = get_component(MINOR);
179 if (!temp) temp = "0";
181 if (where == MINOR) return to_return;
184 if (style == DETAILED) to_return += "revision ";
185 temp = get_component(REVISION);
186 if (!temp) temp = "0";
188 if (where == REVISION) return to_return;
191 if (style == DETAILED) to_return += "build ";
192 temp = get_component(BUILD);
193 if (!temp) temp = "0";
196 // other components don't have handy names.
198 for (int i = BUILD + 1; i < where; i++) {
200 if (style == DETAILED) to_return += a_sprintf("part_%d ", i + 1);
201 temp = get_component(i);
202 if (!temp) temp = "0";
210 version version::from_text(const astring &to_convert)
211 { return version(to_convert); }
213 int version::packed_size() const
215 return _components->packed_size();
218 void version::pack(byte_array &target) const
219 { _components->pack(target); }
221 bool version::unpack(byte_array &source)
223 if (!_components->unpack(source)) return false;
229 #define VR_NEWLINE to_return += "\n"
231 version_record::~version_record()
234 astring version_record::text_form() const
237 to_return += "Description: ";
238 to_return += description;
240 to_return += "File Version: ";
241 to_return += file_version.text_form();
243 to_return += "Internal Name: ";
244 to_return += internal_name;
246 to_return += "Original Name: ";
247 to_return += original_name;
249 to_return += "Product Name: ";
250 to_return += product_name;
252 to_return += "Product Version: ";
253 to_return += product_version.text_form();
255 to_return += "Company Name: ";
256 to_return += company_name;
258 to_return += "Copyright: ";
259 to_return += copyright;
261 to_return += "Trademarks: ";
262 to_return += trademarks;