2 * CDE - Common Desktop Environment
4 * Copyright (c) 1993-2012, The Open Group. All rights reserved.
6 * These libraries and programs are free software; you can
7 * redistribute them and/or modify them under the terms of the GNU
8 * Lesser General Public License as published by the Free Software
9 * Foundation; either version 2 of the License, or (at your option)
12 * These libraries and programs are distributed in the hope that
13 * they will be useful, but WITHOUT ANY WARRANTY; without even the
14 * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU Lesser General Public License for more
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with these librararies and programs; if not, write
20 * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21 * Floor, Boston, MA 02110-1301 USA
24 * $XConsortium: info_lib.C /main/9 1996/12/02 12:47:19 cde-hal $
26 * Copyright (c) 1992 HAL Computer Systems International, Ltd.
27 * All rights reserved. Unpublished -- rights reserved under
28 * the Copyright Laws of the United States. USE OF A COPYRIGHT
29 * NOTICE IS PRECAUTIONARY ONLY AND DOES NOT IMPLY PUBLICATION
32 * THIS SOFTWARE CONTAINS CONFIDENTIAL INFORMATION AND TRADE
33 * SECRETS OF HAL COMPUTER SYSTEMS INTERNATIONAL, LTD. USE,
34 * DISCLOSURE, OR REPRODUCTION IS PROHIBITED WITHOUT THE
35 * PRIOR EXPRESS WRITTEN PERMISSION OF HAL COMPUTER SYSTEMS
38 * RESTRICTED RIGHTS LEGEND
39 * Use, duplication, or disclosure by the Government is subject
40 * to the restrictions as set forth in subparagraph (c)(l)(ii)
41 * of the Rights in Technical Data and Computer Software clause
42 * at DFARS 252.227-7013.
44 * HAL COMPUTER SYSTEMS INTERNATIONAL, LTD.
51 #include "unique_id.h"
52 #include "api/info_lib.h"
53 #include "utility/db_version.h"
54 #include "oliasdb/locator_hd.h"
55 #include "oliasdb/graphic_hd.h"
58 #include <lib/DtSvc/DtUtil2/LocaleXlate.h>
62 extern void report_total();
63 extern void reset_total();
69 typedef char* charPtr;
71 info_lib::info_lib(char** set_name_array, char** list_name_array,
72 char* info_lib_dir, char* selected_base_name,
73 char* infoLibName, int des) :
74 set_nm_list(set_name_array), list_nm_list(list_name_array),
75 f_bad_base_array_size(0), f_bad_info_bases(0),
76 f_bad_info_base_names(0), f_bad_info_base_paths(0), f_descriptor(des)
79 //debug(cerr, info_lib_dir);
80 //debug(cerr, infoLibName);
84 f_obj_dict = new object_dict;
86 if ( info_lib_dir == 0 ) {
87 throw(stringException("NULL info lib path"));
90 if ( check_and_create_dir(info_lib_dir) == false )
91 throw(stringException(
92 form("infolib %s does not exist or can't be created", info_lib_dir)
96 len = MIN(strlen(info_lib_dir), PATHSIZ -1);
97 *((char *) memcpy (info_lib_path, info_lib_dir, len) + len) = '\0';
98 len = MIN(strlen(infoLibName), PATHSIZ -1);
99 *((char *) memcpy (info_lib_name, infoLibName, len) + len) = '\0';
103 if ( exist_file(MAP_FILE_8_3, info_lib_dir) == true ) {
105 map_in = new fstream(form("%s/%s", info_lib_dir, MAP_FILE_8_3), ios::in);
109 if ( !map_in -> getline(info_lib_name, PATHSIZ, '\t') ||
110 !map_in -> getline(info_lib_uid, UIDSIZ, '\n')
113 throw(stringException(
114 form("infolib %s does not have correct name-id entry", info_lib_dir)
119 if ( exist_file(MAP_FILE, info_lib_dir) == true )
120 map_in = new fstream(form("%s/%s", info_lib_dir, MAP_FILE), ios::in);
125 char base_name[PATHSIZ];
126 char base_desc[PATHSIZ];
127 char base_uid[UIDSIZ];
128 char base_locale[PATHSIZ];
129 char db_path_name[PATHSIZ];
131 int major_mm_version = 0;
132 int minor_mm_version = 0;
135 while ( map_in -> getline(base_name, PATHSIZ, '\t') ) {
137 map_in -> getline(base_desc, PATHSIZ, '\t');
139 if ( g_mode_8_3 == 1 ) {
140 map_in -> getline(base_uid, PATHSIZ, '\t');
141 map_in -> getline(base_locale, PATHSIZ, '\t');
146 (*map_in) >> major_mm_version >> minor_mm_version;
150 if ( base_name[0] != CommentChar ) {
152 //debug(cerr, base_name);
153 //debug(cerr, base_desc);
154 //fprintf(stderr, "base_name = %s\n", base_name);
156 char* mmdb_lang = getenv("MMDB_LANG");
157 #ifdef MMDB_LANG_DEBUG
158 cerr << "base_locale=" << base_locale << endl;
160 cerr << "mmdb_lang=" << mmdb_lang << endl;
163 if ((selected_base_name == 0 ||
164 strcmp(selected_base_name, base_name) == 0) &&
165 (mmdb_lang == NULL ||
166 strcmp(mmdb_lang, base_locale) == 0 ||
167 strcmp("C.ISO-8859-1", base_locale) == 0))
170 len = MIN(strlen(info_lib_dir) + strlen(base_name) +1, PATHSIZ -1);
171 *((char *) memcpy (db_path_name,
172 form("%s/%s", info_lib_dir, base_name),
175 mm_version mmv_code(MAJOR, MINOR);
176 mm_version mmv_base_data(2, 1);
177 mm_version mmv_data(major_mm_version, minor_mm_version);
179 ///////////////////////////////////////////////
180 // Hardcoded knowledge of discontinuation of
181 // backward compatibility
182 ///////////////////////////////////////////////
183 if ( mmv_data < mmv_base_data ||
184 mmv_data == mmv_base_data ||
190 if ( f_bad_base_array_size == 0 ||
191 f_bad_base_array_size <= f_bad_info_bases
195 if ( f_bad_base_array_size == 0 ) {
196 f_bad_base_array_size = 10;
197 f_bad_info_base_names = new charPtr[f_bad_base_array_size];
198 f_bad_info_base_paths = new charPtr[f_bad_base_array_size];
200 for (int i=0; i<f_bad_base_array_size; i++) {
201 f_bad_info_base_paths[i] = 0;
202 f_bad_info_base_names[i] = 0;
206 char** x = new charPtr[2*f_bad_base_array_size];
207 char** y = new charPtr[2*f_bad_base_array_size];
209 for (int i=0; i<2*f_bad_base_array_size; i++) {
214 memcpy(x, f_bad_info_base_names, sizeof(charPtr)*f_bad_base_array_size);
215 memcpy(y, f_bad_info_base_paths, sizeof(charPtr)*f_bad_base_array_size);
216 f_bad_base_array_size *= 2;
218 delete f_bad_info_base_names;
219 delete f_bad_info_base_paths;
221 f_bad_info_base_names = x;
222 f_bad_info_base_paths = y;
230 f_bad_info_base_paths[f_bad_info_bases] = strdup(info_lib_dir);
231 f_bad_info_base_names[f_bad_info_bases] = strdup(base_name);
235 MESSAGE(cerr, "Data and code version mismatch");
237 MESSAGE(cerr, form("Data version: v%d.%d",
238 major_mm_version, minor_mm_version
241 MESSAGE(cerr, form("Code version: v%d.%d",
245 MESSAGE(cerr, form("infobase %s is not available.", base_name));
251 _init_info_base(db_path_name, base_name, base_desc, base_uid, base_locale,
252 mm_version(major_mm_version, minor_mm_version));
262 info_lib::~info_lib()
267 info_base* x = (*this)(ind);
273 if ( f_bad_info_base_paths ) {
274 for (int i=0; i<f_bad_base_array_size; i++) {
275 delete f_bad_info_base_paths[i];
277 delete f_bad_info_base_paths;
281 if ( f_bad_info_base_names ) {
282 for (int i=0; i<f_bad_base_array_size; i++) {
283 delete f_bad_info_base_names[i];
285 delete f_bad_info_base_names;
292 /* *********************************************************/
293 // init all bases. play the trick by changing the db_path
294 // value to load all info bases (each has different db_path).
295 /* *********************************************************/
298 info_lib::_init_info_base( const char* base_path,
299 const char* base_name,
300 const char* base_desc,
301 const char* base_uid,
302 const char* base_locale,
308 debug(cerr, base_path);
309 debug(cerr, base_name);
312 //fprintf(stderr, "init_base\n");
313 //fprintf(stderr, "base_path=%s\n", base_path);
314 //fprintf(stderr, "base_name=%s\n", base_name);
318 if ( ( x = get_info_base(base_name)) == 0 ) {
320 if ( exist_dir(base_path) == false )
323 //fprintf(stderr, "try to init %s\n", base_name);
326 f_obj_dict -> init_a_base((char*)base_path, (char*)base_name);
328 x = new info_base(*f_obj_dict, set_nm_list, list_nm_list,
329 base_path, base_name, base_desc, base_uid, base_locale,
333 info_base_list.insert_as_tail(new dlist_void_ptr_cell(x));
336 mcatch (mmdbException &,e)
338 //fprintf(stderr, "in catch block\n");
348 /******************************************/
350 // def_strings array:
352 // def_strings[0] : infobase name
353 // def_strings[1] : infobase textual description
354 // def_strings[2] : define spec file name (full path)
356 /******************************************/
359 info_lib::define_info_base( char* base_name, char* base_desc,
363 //MESSAGE(cerr, "define_info_base()");
364 //debug(cerr, base_name);
365 //debug(cerr, base_desc);
366 //debug(cerr, spec_file_path);
368 char new_db_path[PATHSIZ];
369 char f_name[PATHSIZ];
370 char base_uid[UIDSIZ];
374 len = MIN(strlen(info_lib_path) + strlen(base_name) + 1, PATHSIZ -1);
375 *((char *) memcpy (new_db_path,
376 form("%s/%s", info_lib_path, base_name),
380 len = MIN(strlen(uid), UIDSIZ -1);
381 *((char *) memcpy(base_uid, uid, len) + len) = '\0';
385 info_base* base = get_info_base(base_name) ;
387 /* no checking here. DDK assures unique base name case
391 //////////////////////////
392 // check info base path
393 //////////////////////////
394 if ( check_and_create_dir(new_db_path) == false ) {
395 throw(stringException(form("bad base bath %s", new_db_path)));
398 //////////////////////////
399 // remove any old files
400 //////////////////////////
402 len = MIN(strlen(base_name) + strlen(DATA_FILE_SUFFIX) +1, PATHSIZ -1);
403 *((char *) memcpy(f_name,
404 form("%s.%s", base_name, DATA_FILE_SUFFIX),
406 if ( exist_file(f_name, new_db_path) == true )
407 del_file(f_name, new_db_path);
409 len = MIN(strlen(base_name) + strlen(INDEX_FILE_SUFFIX) + 1, PATHSIZ -1);
410 *((char *) memcpy(f_name,
411 form("%s.%s", base_name, INDEX_FILE_SUFFIX),
413 if ( exist_file(f_name, new_db_path) == true )
414 del_file(f_name, new_db_path);
416 len = MIN(strlen(base_name) + strlen(SCHEMA_FILE_SUFFIX) +1, PATHSIZ -1);
417 *((char *) memcpy(f_name,
418 form("%s.%s", base_name, SCHEMA_FILE_SUFFIX),
420 if ( exist_file(f_name, new_db_path) == true )
421 del_file(f_name, new_db_path);
424 f_obj_dict -> init_a_base(spec_file_path, new_db_path, base_name);
427 if ((lang = getenv("LC_ALL")) == NULL)
428 if ((lang = getenv("LC_CTYPE")) == NULL)
429 if ((lang = getenv("LANG")) == NULL)
433 _DtXlateDb db = NULL;
434 char* std_locale = NULL;
436 if (_DtLcxOpenAllDbs(&db) == 0)
438 char platform[_DtPLATFORM_MAX_LEN + 1];
439 int execver, compver;
441 if (_DtXlateGetXlateEnv(db, platform, &execver, &compver) == 0)
443 _DtLcxXlateOpToStd(db, platform, compver, DtLCX_OPER_SETLOCALE,
444 lang, &std_locale, NULL, NULL, NULL);
451 base = new info_base(*f_obj_dict, set_nm_list, list_nm_list,
452 new_db_path, base_name, base_desc, base_uid,
454 std_locale ? std_locale : lang,
458 mm_version(MAJOR, MINOR)
461 info_base_list.insert_as_tail(new dlist_void_ptr_cell(base));
463 /*************************************/
464 // add the base name and description
466 /*************************************/
467 char* lib_nm = form("%s/%s", info_lib_path, MAP_FILE_8_3);
469 fstream nm_out(lib_nm, ios::out | ios::app);
470 // fstream nm_out(lib_nm, ios::app, open_file_prot());
473 MESSAGE(cerr, form("can't open %s/%s for append",
474 info_lib_path, MAP_FILE_8_3)
476 throw(streamException(nm_out.rdstate()));
479 if ( bytes(lib_nm) == 0 ) {
480 char* lib_entry = form("%s\t%s\n", info_lib_name, unique_id());
482 if ( !(nm_out << lib_entry) ) {
484 form("write %s.%s failed", info_lib_path, MAP_FILE_8_3));
485 throw(streamException(nm_out.rdstate()));
489 char* base_entry = form("%s\t%s\t%s\t%s\t%d\t%d\n",
490 base_name, base_desc, base_uid,
492 std_locale ? std_locale: lang,
503 if ( !(nm_out << base_entry) ) {
504 MESSAGE(cerr, form("write %s.%s failed", info_lib_path, MAP_FILE_8_3));
505 throw(streamException(nm_out.rdstate()));
510 if ( nm_out.fail() ) {
511 MESSAGE(cerr, form("close %s.%s failed", info_lib_path, MAP_FILE_8_3));
512 throw(streamException(nm_out.rdstate()));
518 //MESSAGE(cerr, "define() done");
522 info_base* info_lib::get_info_base(const char* info_base_nm)
528 info_base* x = (*this)(ind);
532 debug(cerr, x -> base_name);
533 debug(cerr, info_base_nm);
536 if ( strcmp ( x -> base_name, info_base_nm) == 0 )
545 int info_lib::num_of_bases()
547 return info_base_list.count();
551 /*************************/
552 // iteration funcstions
553 /*************************/
556 int info_lib::first()
558 return info_base_list.first();
561 info_base* info_lib::operator()(int ind)
563 return (info_base*)(((dlist_void_ptr_cell*)ind)->void_ptr());
566 void info_lib::next(int& ind)
568 info_base_list.next(ind) ;
573 int info_lib::bad_infobases()
575 return f_bad_info_bases;
579 const char* info_lib::get_bad_infobase_path(int x)
581 if ( x <= 0 || x > f_bad_info_bases )
584 return f_bad_info_base_paths[x-1];
587 const char* info_lib::get_bad_infobase_name(int x)
589 if ( x <= 0 || x > f_bad_info_bases )
592 return f_bad_info_base_names[x-1];
597 info_lib::getInfobaseByComponent(const char *locator_string, enum TestSelector sel)
600 if ( locator_string == 0 )
612 throw(stringException("null info_base ptr"));
614 mtry { // since an infobase may not have any graphics, we catch
615 // any exceptions there and try next infobase.
620 locator_smart_ptr loc(ib, locator_string);
622 //fprintf(stderr, "inside-loc-string=%s\n", loc.inside_node_locator_str());
623 //fprintf(stderr, "loc-string=%s\n", locator_string);
624 if ( strcmp( loc.inside_node_locator_str(), locator_string) == 0 ) {
631 graphic_smart_ptr graphic(ib, locator_string);
633 if ( strcmp( graphic.locator(), locator_string) == 0 ) {
640 mcatch (mmdbException &,e)
652 info_lib::getInfobasesByComponent(char **locator_strings, int count, enum TestSelector sel)
654 info_base** ibs = new info_basePtr[count];
656 for ( i=0; i<count; ibs[i++] = 0 );
667 throw(stringException("null info_base ptr"));
669 for ( i=0; i<count; i++ ) {
673 if ( locator_strings[i] && ibs[i] == 0 ) {
677 locator_smart_ptr loc(ib, locator_strings[i]);
679 if ( strcmp( loc.inside_node_locator_str(),
680 locator_strings[i]) == 0
688 graphic_smart_ptr graphic(ib, locator_strings[i]);
690 if ( strcmp( graphic.locator(),
691 locator_strings[i]) == 0
700 mcatch (mmdbException &,e)