1#************************************************************** 2# 3# Licensed to the Apache Software Foundation (ASF) under one 4# or more contributor license agreements. See the NOTICE file 5# distributed with this work for additional information 6# regarding copyright ownership. The ASF licenses this file 7# to you under the Apache License, Version 2.0 (the 8# "License"); you may not use this file except in compliance 9# with the License. You may obtain a copy of the License at 10# 11# http://www.apache.org/licenses/LICENSE-2.0 12# 13# Unless required by applicable law or agreed to in writing, 14# software distributed under the License is distributed on an 15# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16# KIND, either express or implied. See the License for the 17# specific language governing permissions and limitations 18# under the License. 19# 20#************************************************************** 21 22 23 24package installer::scriptitems; 25 26use installer::converter; 27use installer::existence; 28use installer::exiter; 29use installer::globals; 30use installer::languages; 31use installer::logger; 32use installer::pathanalyzer; 33use installer::remover; 34use installer::systemactions; 35 36use File::Spec; 37use SvnRevision; 38 39################################################################ 40# Resolving the GID for the directories defined in setup script 41################################################################ 42 43sub resolve_all_directory_names 44{ 45 my ($directoryarrayref) = @_; 46 47 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::resolve_all_directory_names : $#{$directoryarrayref}"); } 48 49 # After this procedure the hash shall contain the complete language 50 # dependent path, not only the language dependent HostName. 51 52 my ($key, $value, $parentvalue, $parentgid, $parentdirectoryhashref); 53 54 for ( my $i = 0; $i <= $#{$directoryarrayref}; $i++ ) 55 { 56 my $directoryhashref = ${$directoryarrayref}[$i]; 57 my $gid = $directoryhashref-> {'gid'}; 58 my $parentid = $directoryhashref-> {'ParentID'}; 59 60 if ( $parentid ne "PREDEFINED_PROGDIR" ) 61 { 62 # find the array of the parentid, which has to be defined before in setup script 63 # and is therefore listed before in this array 64 65 for ( my $j = 0; $j <= $i; $j++ ) 66 { 67 $parentdirectoryhashref = ${$directoryarrayref}[$j]; 68 $parentgid = $parentdirectoryhashref->{'gid'}; 69 70 if ( $parentid eq $parentgid) 71 { 72 last; 73 } 74 } 75 76 # and now we can put the path together 77 # But take care of the languages! 78 79 my $dirismultilingual = $directoryhashref->{'ismultilingual'}; 80 my $parentismultilingual = $parentdirectoryhashref->{'ismultilingual'}; 81 82 # First: Both directories are language independent or both directories are language dependent 83 84 if ((( ! $dirismultilingual ) && ( ! $parentismultilingual )) || 85 (( $dirismultilingual ) && ( $parentismultilingual ))) 86 { 87 foreach $key (keys %{$directoryhashref}) 88 { 89 # the key ("HostName (en-US)") must be usable for both hashes 90 91 if ( $key =~ /\bHostName\b/ ) 92 { 93 $parentvalue = ""; 94 $value = $directoryhashref->{$key}; 95 if ( $parentdirectoryhashref->{$key} ) { $parentvalue = $parentdirectoryhashref->{$key}; } 96 97 # It is possible, that in scp project, a directory is defined in more languages than 98 # the directory parent (happened after automatic generation of macros.inc). 99 # Therefore this is checked now and written with a warning into the logfile. 100 # This is no error, because (in most cases) the concerned language is not build. 101 102 if ($parentvalue eq "") 103 { 104 $directoryhashref->{$key} = "FAILURE"; 105 my $infoline = "WARNING: No hostname for $parentid with \"$key\". Needed by child directory $gid !\n"; 106 push( @installer::globals::globallogfileinfo, $infoline); 107 } 108 else 109 { 110 $directoryhashref->{$key} = $parentvalue . $installer::globals::separator . $value; 111 } 112 } 113 } 114 } 115 116 # Second: The directory is language dependent, the parent not 117 118 if (( $dirismultilingual ) && ( ! $parentismultilingual )) 119 { 120 $parentvalue = $parentdirectoryhashref->{'HostName'}; # there is only one 121 122 foreach $key (keys %{$directoryhashref}) # the current directory 123 { 124 if ( $key =~ /\bHostName\b/ ) 125 { 126 $value = $directoryhashref->{$key}; 127 $directoryhashref->{$key} = $parentvalue . $installer::globals::separator . $value; 128 } 129 } 130 } 131 132 # Third: The directory is not language dependent, the parent is language dependent 133 134 if (( ! $dirismultilingual ) && ( $parentismultilingual )) 135 { 136 $value = $directoryhashref->{'HostName'}; # there is only one 137 delete($directoryhashref->{'HostName'}); 138 139 foreach $key (keys %{$parentdirectoryhashref}) # the parent directory 140 { 141 if ( $key =~ /\bHostName\b/ ) 142 { 143 $parentvalue = $parentdirectoryhashref->{$key}; # there is only one 144 $directoryhashref->{$key} = $parentvalue . $installer::globals::separator . $value; 145 } 146 } 147 148 $directoryhashref->{'ismultilingual'} = 1; # now this directory is also language dependent 149 } 150 } 151 } 152} 153 154############################################################################# 155# Files with flag DELETE_ONLY do not need to be packed into installation set 156############################################################################# 157 158sub remove_delete_only_files_from_productlists 159{ 160 my ($productarrayref) = @_; 161 162 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_delete_only_files_from_productlists : $#{$productarrayref}"); } 163 164 my @newitems = (); 165 166 for ( my $i = 0; $i <= $#{$productarrayref}; $i++ ) 167 { 168 my $oneitem = ${$productarrayref}[$i]; 169 my $styles = ""; 170 171 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 172 173 if (!($styles =~ /\bDELETE_ONLY\b/)) 174 { 175 push(@newitems, $oneitem); 176 } 177 } 178 179 return \@newitems; 180} 181 182############################################################################# 183# Files with flag NOT_IN_SUITE do not need to be packed into 184# Suite installation sets 185############################################################################# 186 187sub remove_notinsuite_files_from_productlists 188{ 189 my ($productarrayref) = @_; 190 191 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_notinsuite_files_from_productlists : $#{$productarrayref}"); } 192 193 my @newitems = (); 194 195 for ( my $i = 0; $i <= $#{$productarrayref}; $i++ ) 196 { 197 my $oneitem = ${$productarrayref}[$i]; 198 my $styles = ""; 199 200 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 201 202 if (!($styles =~ /\bNOT_IN_SUITE\b/)) 203 { 204 push(@newitems, $oneitem); 205 } 206 else 207 { 208 my $infoline = "INFO: Flag NOT_IN_SUITE \-\> Removing $oneitem->{'gid'} from file list.\n"; 209 push( @installer::globals::globallogfileinfo, $infoline); 210 } 211 } 212 213 return \@newitems; 214} 215 216############################################################################# 217# Files with flag NOT_IN_SUITE do not need to be packed into 218# Suite installation sets 219############################################################################# 220 221sub remove_office_start_language_files 222{ 223 my ($productarrayref) = @_; 224 225 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_notinsuite_files_from_productlists : $#{$productarrayref}"); } 226 227 my @newitems = (); 228 229 for ( my $i = 0; $i <= $#{$productarrayref}; $i++ ) 230 { 231 my $oneitem = ${$productarrayref}[$i]; 232 my $styles = ""; 233 234 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 235 236 if (!($styles =~ /\bSET_OFFICE_LANGUAGE\b/)) 237 { 238 push(@newitems, $oneitem); 239 } 240 else 241 { 242 my $infoline = "INFO: Flag SET_OFFICE_LANGUAGE \-\> Removing $oneitem->{'gid'} from file list.\n"; 243 push( @installer::globals::logfileinfo, $infoline); 244 } 245 } 246 247 return \@newitems; 248} 249 250############################################################################# 251# Registryitems for Uninstall have to be removed 252############################################################################# 253 254sub remove_uninstall_regitems_from_script 255{ 256 my ($registryarrayref) = @_; 257 258 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_uninstall_regitems_from_script : $#{$registryarrayref}"); } 259 260 my @newitems = (); 261 262 for ( my $i = 0; $i <= $#{$registryarrayref}; $i++ ) 263 { 264 my $oneitem = ${$registryarrayref}[$i]; 265 my $subkey = ""; 266 267 if ( $oneitem->{'Subkey'} ) { $subkey = $oneitem->{'Subkey'}; } 268 269 if ( $subkey =~ /Software\\Microsoft\\Windows\\CurrentVersion\\Uninstall/ ) { next; } 270 271 push(@newitems, $oneitem); 272 } 273 274 return \@newitems; 275} 276 277############################################################################## 278# Searching the language module for a specified language 279############################################################################## 280 281sub get_languagespecific_module 282{ 283 my ( $lang, $modulestring ) = @_; 284 285 my $langmodulestring = ""; 286 287 my $module; 288 foreach $module ( keys %installer::globals::alllangmodules ) 289 { 290 if (( $installer::globals::alllangmodules{$module} eq $lang ) && ( $modulestring =~ /\b$module\b/ )) 291 { 292 $langmodulestring = "$langmodulestring,$module"; 293 } 294 } 295 296 $langmodulestring =~ s/^\s*,//; 297 298 if ( $langmodulestring eq "" ) { installer::exiter::exit_program("ERROR: No language pack module found for language $lang in string \"$modulestring\"!", "get_languagespecific_module"); } 299 300 return $langmodulestring; 301} 302 303############################################################################## 304# Removing all items in product lists which do not have the correct languages 305############################################################################## 306 307sub resolving_all_languages_in_productlists 308{ 309 my ($productarrayref, $languagesarrayref) = @_; 310 311 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::resolving_all_languages_in_productlists : $#{$productarrayref} : $#{$languagesarrayref}"); } 312 313 my @itemsinalllanguages = (); 314 315 my ($key, $value); 316 317 for ( my $i = 0; $i <= $#{$productarrayref}; $i++ ) 318 { 319 my $oneitem = ${$productarrayref}[$i]; 320 321 my $ismultilingual = $oneitem->{'ismultilingual'}; 322 323 if (!($ismultilingual)) # nothing to do with single language items 324 { 325 $oneitem->{'specificlanguage'} = ""; 326 push(@itemsinalllanguages, $oneitem); 327 } 328 else #all language dependent files 329 { 330 for ( my $j = 0; $j <= $#{$languagesarrayref}; $j++ ) # iterating over all languages 331 { 332 my $onelanguage = ${$languagesarrayref}[$j]; 333 334 my %oneitemhash = (); 335 336 foreach $key (keys %{$oneitem}) 337 { 338 if ( $key =~ /\(\S+\)/ ) # this are the language dependent keys 339 { 340 if ( $key =~ /\(\Q$onelanguage\E\)/ ) 341 { 342 $value = $oneitem->{$key}; 343 $oneitemhash{$key} = $value; 344 } 345 } 346 else 347 { 348 $value = $oneitem->{$key}; 349 $oneitemhash{$key} = $value; 350 } 351 } 352 353 $oneitemhash{'specificlanguage'} = $onelanguage; 354 355 if ( $oneitemhash{'haslanguagemodule'} ) 356 { 357 my $langmodulestring = get_languagespecific_module($onelanguage, $oneitemhash{'modules'}); 358 $oneitemhash{'modules'} = $langmodulestring; 359 } 360 361 push(@itemsinalllanguages, \%oneitemhash); 362 } 363 } 364 } 365 366 return \@itemsinalllanguages; 367} 368 369################################################################################ 370# Removing all modules, that have the flag LANGUAGEMODULE, but do not 371# have the correct language 372################################################################################ 373 374sub remove_not_required_language_modules 375{ 376 my ($modulesarrayref, $languagesarrayref) = @_; 377 378 my @allmodules = (); 379 380 for ( my $i = 0; $i <= $#{$modulesarrayref}; $i++ ) 381 { 382 my $module = ${$modulesarrayref}[$i]; 383 my $styles = ""; 384 if ( $module->{'Styles'} ) { $styles = $module->{'Styles'}; } 385 386 if ( $styles =~ /\bLANGUAGEMODULE\b/ ) 387 { 388 if ( ! exists($module->{'Language'}) ) { installer::exiter::exit_program("ERROR: \"$module->{'gid'}\" has flag LANGUAGEMODULE, but does not know its language!", "remove_not_required_language_modules"); } 389 my $modulelanguage = $module->{'Language'}; 390 # checking, if language is required 391 my $doinclude = 0; 392 for ( my $j = 0; $j <= $#{$languagesarrayref}; $j++ ) 393 { 394 my $onelanguage = ${$languagesarrayref}[$j]; 395 if ( $onelanguage eq $modulelanguage ) 396 { 397 $doinclude = 1; 398 last; 399 } 400 } 401 402 if ( $doinclude ) { push(@allmodules, $module); } 403 } 404 else 405 { 406 push(@allmodules, $module); 407 } 408 } 409 410 return \@allmodules; 411} 412 413################################################################################ 414# Removing all modules, that have a spellchecker language that is not 415# required for this product (spellchecker selection). 416# All required spellchecker languages are stored in 417# %installer::globals::spellcheckerlanguagehash 418################################################################################ 419 420sub remove_not_required_spellcheckerlanguage_modules 421{ 422 my ($modulesarrayref) = @_; 423 424 my $infoline = ""; 425 my @allmodules = (); 426 427 for ( my $i = 0; $i <= $#{$modulesarrayref}; $i++ ) 428 { 429 my $module = ${$modulesarrayref}[$i]; 430 if ( $module->{'Spellcheckerlanguage'} ) # selecting modules with Spellcheckerlanguage 431 { 432 if ( exists($installer::globals::spellcheckerlanguagehash{$module->{'Spellcheckerlanguage'}}) ) 433 { 434 push(@allmodules, $module); 435 } 436 else 437 { 438 $infoline = "Spellchecker selection: Removing module $module->{'gid'}\n"; 439 push( @installer::globals::logfileinfo, $infoline); 440 441 # Collecting all files at modules that are removed 442 443 if ( $module->{'Files'} ) 444 { 445 if ( $module->{'Files'} =~ /^\s*\((.*?)\)\s*$/ ) 446 { 447 my $filelist = $1; 448 449 my $filelisthash = installer::converter::convert_stringlist_into_hash(\$filelist, ","); 450 foreach my $onefile ( keys %{$filelisthash} ) { $installer::globals::spellcheckerfilehash{$onefile} = 1; } 451 } 452 } 453 } 454 } 455 else 456 { 457 push(@allmodules, $module); 458 } 459 } 460 461 return \@allmodules; 462} 463 464################################################################################ 465# Removing all modules, that belong to a module that was removed 466# in "remove_not_required_spellcheckerlanguage_modules" because of the 467# spellchecker language. The files belonging to the modules are collected 468# in %installer::globals::spellcheckerfilehash. 469################################################################################ 470 471sub remove_not_required_spellcheckerlanguage_files 472{ 473 my ($filesarrayref) = @_; 474 475 my @filesarray = (); 476 my $infoline = ""; 477 478 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 479 { 480 my $onefile = ${$filesarrayref}[$i]; 481 if ( exists($installer::globals::spellcheckerfilehash{$onefile->{'gid'}}) ) 482 { 483 $infoline = "Spellchecker selection: Removing file $onefile->{'gid'}\n"; 484 push( @installer::globals::logfileinfo, $infoline); 485 next; 486 } 487 push(@filesarray, $onefile); 488 } 489 490 return \@filesarray; 491} 492 493################################################################################ 494# Looking for directories without correct HostName 495################################################################################ 496 497sub checking_directories_with_corrupt_hostname 498{ 499 my ($dirsref, $languagesarrayref) = @_; 500 501 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 502 { 503 my $onedir = ${$dirsref}[$i]; 504 505 my $hostname = ""; 506 507 if ( $onedir->{'HostName'} ) { $hostname = $onedir->{'HostName'}; } 508 509 if ( $hostname eq "" ) 510 { 511 my $langstring = ""; 512 for ( my $j = 0; $j <= $#{$languagesarrayref}; $j++ ) { $langstring .= ${$languagesarrayref}[$j] . " "; } 513 installer::exiter::exit_program("ERROR: HostName not defined for $onedir->{'gid'} for specified language. Probably you wanted to create an installation set, in a language not defined in scp2 project. You selected the following language(s): $langstring", "checking_directories_with_corrupt_hostname"); 514 } 515 516 if ( $hostname eq "FAILURE" ) 517 { 518 installer::exiter::exit_program("ERROR: Could not create HostName for $onedir->{'gid'} (missing language at parent). See logfile warning for more info!", "checking_directories_with_corrupt_hostname"); 519 } 520 } 521} 522 523################################################################################ 524# Setting global properties 525################################################################################ 526 527sub set_global_directory_hostnames 528{ 529 my ($dirsref, $allvariables) = @_; 530 531 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 532 { 533 my $onedir = ${$dirsref}[$i]; 534 my $styles = ""; 535 if ( $onedir->{'Styles'} ) { $styles = $onedir->{'Styles'}; } 536 537 if ( $styles =~ /\bOFFICEDIRECTORY\b/ ) 538 { 539 $installer::globals::officedirhostname = $onedir->{'HostName'}; 540 $installer::globals::officedirgid = $onedir->{'gid'}; 541 $allvariables->{'OFFICEDIRECTORYHOSTNAME'} = $installer::globals::officedirhostname; 542 } 543 if ( $styles =~ /\bSUNDIRECTORY\b/ ) 544 { 545 $installer::globals::sundirhostname = $onedir->{'HostName'}; 546 $installer::globals::sundirgid = $onedir->{'gid'}; 547 $allvariables->{'SUNDIRECTORYHOSTNAME'} = $installer::globals::sundirhostname; 548 } 549 } 550} 551 552######################################################## 553# Recursively defined procedure to order 554# modules and directories 555######################################################## 556 557sub get_children 558{ 559 my ($allitems, $startparent, $newitemorder) = @_; 560 561 for ( my $i = 0; $i <= $#{$allitems}; $i++ ) 562 { 563 my $gid = ${$allitems}[$i]->{'gid'}; 564 my $parent = ""; 565 if ( ${$allitems}[$i]->{'ParentID'} ) { $parent = ${$allitems}[$i]->{'ParentID'}; } 566 567 if ( $parent eq $startparent ) 568 { 569 push(@{$newitemorder}, ${$allitems}[$i]); 570 my $parent = $gid; 571 get_children($allitems, $parent, $newitemorder); # recursive! 572 } 573 } 574} 575 576################################################################################ 577# Using different HostName for language packs 578################################################################################ 579 580sub use_langpack_hostname 581{ 582 my ($dirsref) = @_; 583 584 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 585 { 586 my $onedir = ${$dirsref}[$i]; 587 if (( $onedir->{'LangPackHostName'} ) && ( $onedir->{'LangPackHostName'} ne "" )) { $onedir->{'HostName'} = $onedir->{'LangPackHostName'}; } 588 } 589} 590 591################################################################################ 592# Using different HostName for language packs 593################################################################################ 594 595sub use_patch_hostname 596{ 597 my ($dirsref) = @_; 598 599 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 600 { 601 my $onedir = ${$dirsref}[$i]; 602 if (( $onedir->{'PatchHostName'} ) && ( $onedir->{'PatchHostName'} ne "" )) { $onedir->{'HostName'} = $onedir->{'PatchHostName'}; } 603 } 604} 605 606################################################################################ 607# Using langpack copy action for language packs 608################################################################################ 609 610sub use_langpack_copy_scpaction 611{ 612 my ($scpactionsref) = @_; 613 614 for ( my $i = 0; $i <= $#{$scpactionsref}; $i++ ) 615 { 616 my $onescpaction = ${$scpactionsref}[$i]; 617 if (( $onescpaction->{'LangPackCopy'} ) && ( $onescpaction->{'LangPackCopy'} ne "" )) { $onescpaction->{'Copy'} = $onescpaction->{'LangPackCopy'}; } 618 } 619} 620 621################################################################################ 622# Using copy patch action 623################################################################################ 624 625sub use_patch_copy_scpaction 626{ 627 my ($scpactionsref) = @_; 628 629 for ( my $i = 0; $i <= $#{$scpactionsref}; $i++ ) 630 { 631 my $onescpaction = ${$scpactionsref}[$i]; 632 if (( $onescpaction->{'PatchCopy'} ) && ( $onescpaction->{'PatchCopy'} ne "" )) { $onescpaction->{'Copy'} = $onescpaction->{'PatchCopy'}; } 633 } 634} 635 636################################################################################ 637# Using dev copy patch action for developer snapshot builds 638################################################################################ 639 640sub use_dev_copy_scpaction 641{ 642 my ($scpactionsref) = @_; 643 644 for ( my $i = 0; $i <= $#{$scpactionsref}; $i++ ) 645 { 646 my $onescpaction = ${$scpactionsref}[$i]; 647 if (( $onescpaction->{'DevCopy'} ) && ( $onescpaction->{'DevCopy'} ne "" )) { $onescpaction->{'Copy'} = $onescpaction->{'DevCopy'}; } 648 } 649} 650 651################################################################################ 652# Shifting parent directories of URE and Basis layer, so that 653# these directories are located below the Brand layer. 654# Style: SHIFT_BASIS_INTO_BRAND_LAYER 655################################################################################ 656 657sub shift_basis_directory_parents 658{ 659 my ($dirsref) = @_; 660 661 my @alldirs = (); 662 my @savedirs = (); 663 my @shifteddirs = (); 664 665 my $officedirgid = ""; 666 667 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 668 { 669 my $onedir = ${$dirsref}[$i]; 670 my $styles = ""; 671 if ( $onedir->{'Styles'} ) { $styles = $onedir->{'Styles'}; } 672 673 if ( $styles =~ /\bOFFICEDIRECTORY\b/ ) { $officedirgid = $onedir->{'gid'}; } 674 } 675 676 if ( $officedirgid ne "" ) 677 { 678 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 679 { 680 my $onedir = ${$dirsref}[$i]; 681 my $styles = ""; 682 if ( $onedir->{'Styles'} ) { $styles = $onedir->{'Styles'}; } 683 684 if (( $styles =~ /\bBASISDIRECTORY\b/ ) || ( $styles =~ /\bUREDIRECTORY\b/ )) 685 { 686 $onedir->{'ParentID'} = $officedirgid; 687 } 688 } 689 690 # Sorting directories 691 my $startgid = "PREDEFINED_PROGDIR"; 692 get_children($dirsref, $startgid, \@alldirs); 693 } 694 695 return \@alldirs; 696} 697 698################################################################################ 699# Setting the name of the directory with style OFFICEDIRECTORY. 700# The name can be defined in property OFFICEDIRECTORYNAME. 701################################################################################ 702 703sub set_officedirectory_name 704{ 705 my ($dirsref, $officedirname) = @_; 706 707 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 708 { 709 my $onedir = ${$dirsref}[$i]; 710 my $styles = ""; 711 if ( $onedir->{'Styles'} ) { $styles = $onedir->{'Styles'}; } 712 if ( $styles =~ /\bOFFICEDIRECTORY\b/ ) 713 { 714 $onedir->{'HostName'} = $officedirname; 715 last; 716 } 717 } 718} 719 720################################################################################ 721# Simplifying the name for language dependent items from "Name (xy)" to "Name" 722################################################################################ 723 724sub changing_name_of_language_dependent_keys 725{ 726 my ($itemsarrayref) = @_; 727 728 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::changing_name_of_language_dependent_keys : $#{$itemsarrayref}"); } 729 730 # Changing key for multilingual items from "Name ( )" to "Name" or "HostName ( )" to "HostName" 731 732 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 733 { 734 my $oneitem = ${$itemsarrayref}[$i]; 735 my $onelanguage = $oneitem->{'specificlanguage'}; 736 737 if (!($onelanguage eq "" )) # language dependent item 738 { 739 my $itemkey; 740 741 foreach $itemkey (keys %{$oneitem}) 742 { 743 if ( $itemkey =~ /^\s*(\S+?)\s+\(\S+\)\s*$/ ) 744 { 745 my $newitemkey = $1; 746 my $itemvalue = $oneitem->{$itemkey}; 747 $oneitem->{$newitemkey} = $itemvalue; 748 delete($oneitem->{$itemkey}); 749 } 750 } 751 } 752 } 753} 754 755################################################################################ 756# Collecting language specific names for language packs 757################################################################################ 758 759sub collect_language_specific_names 760{ 761 my ($itemsarrayref) = @_; 762 763 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 764 { 765 my $oneitem = ${$itemsarrayref}[$i]; 766 my $styles = ""; 767 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 768 769 if ( $styles =~ /\bUSELANGUAGENAME\b/ ) 770 { 771 my $language = ""; 772 if ( $oneitem->{'Language'} ) { $language = $oneitem->{'Language'}; } 773 my $specificlanguage = ""; 774 if ( $oneitem->{'specificlanguage'} ) { $specificlanguage = $oneitem->{'specificlanguage'}; } 775 776 if (( $language ne "" ) && ( $language eq $specificlanguage )) 777 { 778 if (! installer::existence::exists_in_array($oneitem->{'Name'}, \@installer::globals::languagenames )) 779 { 780 push(@installer::globals::languagenames, $oneitem->{'Name'}); 781 } 782 } 783 } 784 } 785} 786 787################################################################################ 788# Replacement of setup variables in ConfigurationItems and ProfileItems 789# <productkey>, <buildid>, <sequence_languages>, <productcode>, <upgradecode>, <productupdate> 790################################################################################ 791 792sub replace_setup_variables 793{ 794 my ($itemsarrayref, $languagestringref, $hashref) = @_; 795 796 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::replace_setup_variables : $#{$itemsarrayref} : $$languagestringref : $hashref->{'PRODUCTNAME'}"); } 797 798 my $languagesstring = $$languagestringref; 799 $languagesstring =~ s/\_/ /g; # replacing underscore with whitespace 800 # $languagesstring is "01 49" instead of "en-US de" 801 installer::languages::fake_languagesstring(\$languagesstring); 802 803 my $productname = $hashref->{'PRODUCTNAME'}; 804 my $productversion = $hashref->{'PRODUCTVERSION'}; 805 my $userdirproductversion = ""; 806 if ( $hashref->{'USERDIRPRODUCTVERSION'} ) { $userdirproductversion = $hashref->{'USERDIRPRODUCTVERSION'}; } 807 my $productkey = $productname . " " . $productversion; 808 809 my $scsrevision = SvnRevision::DetectRevisionId(File::Spec->catfile($ENV{'SRC_ROOT'}, File::Spec->updir())); 810 811 # string $buildid, which is used to replace the setup variable <buildid> 812 813 my $localminor = "flat"; 814 if ( $installer::globals::minor ne "" ) { $localminor = $installer::globals::minor; } 815 else { $localminor = $installer::globals::lastminor; } 816 817 my $localbuild = $installer::globals::build; 818 819 if ( $localbuild =~ /^\s*(\w+?)(\d+)\s*$/ ) { $localbuild = $2; } # using "680" instead of "src680" 820 821 my $buildidstring = $localbuild . $localminor . "(Build:" . $installer::globals::buildid . ")"; 822 823 # the environment variable CWS_WORK_STAMP is set only in CWS 824 if ( $ENV{'CWS_WORK_STAMP'} ) { $buildidstring = $buildidstring . "\[CWS\:" . $ENV{'CWS_WORK_STAMP'} . "\]"; } 825 826 if ( $localminor =~ /^\s*\w(\d+)\w*\s*$/ ) { $localminor = $1; } 827 828 # $updateid 829 my $updateid = $productname . "_" . $userdirproductversion . "_" . $$languagestringref; 830 $updateid =~ s/ /_/g; 831 832 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 833 { 834 my $oneitem = ${$itemsarrayref}[$i]; 835 my $value = $oneitem->{'Value'}; 836 837 $value =~ s/\<buildid\>/$buildidstring/; 838 $value =~ s/\<scsrevision\>/$scsrevision/; 839 $value =~ s/\<sequence_languages\>/$languagesstring/; 840 $value =~ s/\<productkey\>/$productkey/; 841 $value =~ s/\<productcode\>/$installer::globals::productcode/; 842 $value =~ s/\<upgradecode\>/$installer::globals::upgradecode/; 843 $value =~ s/\<alllanguages\>/$languagesstring/; 844 $value =~ s/\<productmajor\>/$localbuild/; 845 $value =~ s/\<productminor\>/$localminor/; 846 $value =~ s/\<productbuildid\>/$installer::globals::buildid/; 847 $value =~ s/\<sourceid\>/$installer::globals::build/; 848 $value =~ s/\<updateid\>/$updateid/; 849 $value =~ s/\<pkgformat\>/$installer::globals::packageformat/; 850 851 $oneitem->{'Value'} = $value; 852 } 853} 854 855################################################################################ 856# By defining variable LOCALUSERDIR in *.lst it is possible to change 857# the standard destination of user directory defined in scp2 ($SYSUSERCONFIG). 858################################################################################ 859 860sub replace_userdir_variable 861{ 862 my ($itemsarrayref) = @_; 863 864 my $userdir = ""; 865 if ( $allvariableshashref->{'LOCALUSERDIR'} ) { $userdir = $allvariableshashref->{'LOCALUSERDIR'}; } 866 else { $userdir = $installer::globals::simpledefaultuserdir; } 867 868 if ( $userdir ne "" ) 869 { 870 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 871 { 872 my $oneitem = ${$itemsarrayref}[$i]; 873 $oneitem->{'Value'} =~ s/\$SYSUSERCONFIG/$userdir/; 874 } 875 } 876} 877 878##################################################################################### 879# Files and ConfigurationItems are not included for all languages. 880# For instance asian fonts. These can be removed, if no "Name" is found. 881# ConfigurationItems are not always defined in the linguistic configuration file. 882# The "Key" cannot be found for them. 883##################################################################################### 884 885sub remove_non_existent_languages_in_productlists 886{ 887 my ($itemsarrayref, $languagestringref, $searchkey, $itemtype) = @_; 888 889 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_non_existent_languages_in_productlists : $#{$itemsarrayref} : $$languagestringref : $searchkey : $itemtype"); } 890 891 # Removing of all non existent files, for instance asian fonts 892 893 installer::logger::include_header_into_logfile("Removing for this language $$languagestringref:"); 894 895 my @allexistentitems = (); 896 897 my $infoline; 898 899 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 900 { 901 my $oneitem = ${$itemsarrayref}[$i]; 902 my $oneitemname = ""; # $searchkey is "Name" for files and "Key" for ConfigurationItems 903 904 if ( $oneitem->{$searchkey} ) { $oneitemname = $oneitem->{$searchkey} } 905 906 my $itemtoberemoved = 0; 907 908 if ($oneitemname eq "") # for instance asian font in english installation set 909 { 910 $itemtoberemoved = 1; 911 } 912 913 if ($itemtoberemoved) 914 { 915 $infoline = "WARNING: Language $$languagestringref: No $itemtype packed for $oneitem->{'gid'}!\n"; 916 push( @installer::globals::logfileinfo, $infoline); 917 } 918 else 919 { 920 push(@allexistentitems, $oneitem); 921 } 922 } 923 924 $infoline = "\n"; 925 push( @installer::globals::logfileinfo, $infoline); 926 927 return \@allexistentitems; 928} 929 930######################################################################## 931# Input is the directory gid, output the "HostName" of the directory 932######################################################################## 933 934sub get_Directoryname_From_Directorygid 935{ 936 my ($dirsarrayref ,$searchgid, $onelanguage, $oneitemgid) = @_; 937 938 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::get_Directoryname_From_Directorygid : $#{$dirsarrayref} : $searchgid : $onelanguage"); } 939 940 my $directoryname = ""; 941 my $onedirectory; 942 my $foundgid = 0; 943 944 for ( my $i = 0; $i <= $#{$dirsarrayref}; $i++ ) 945 { 946 $onedirectory = ${$dirsarrayref}[$i]; 947 my $directorygid = $onedirectory->{'gid'}; 948 949 if ($directorygid eq $searchgid) 950 { 951 $foundgid = 1; 952 last; 953 } 954 } 955 956 if (!($foundgid)) 957 { 958 installer::exiter::exit_program("ERROR: Gid $searchgid not defined in $installer::globals::setupscriptname", "get_Directoryname_From_Directorygid"); 959 } 960 961 if ( ! ( $onedirectory->{'ismultilingual'} )) # the directory is not language dependent 962 { 963 $directoryname = $onedirectory->{'HostName'}; 964 } 965 else 966 { 967 $directoryname = $onedirectory->{"HostName ($onelanguage)"}; 968 } 969 970 # gid_Dir_Template_Wizard_Letter is defined as language dependent directory, but the file gid_Dir_Template_Wizard_Letter 971 # is not language dependent. Therefore $onelanguage is not defined. But which language is the correct language for the 972 # directory? 973 # Perhaps better solution: In scp it must be forbidden to have a language independent file in a language dependent directory. 974 975 if (( ! $directoryname ) && ( $onelanguage eq "" )) 976 { 977 installer::exiter::exit_program("ERROR (in scp): Directory $searchgid is language dependent, but not $oneitemgid inside this directory", "get_Directoryname_From_Directorygid"); 978 } 979 980 return \$directoryname; 981} 982 983################################################################## 984# Getting destination direcotory for links, files and profiles 985################################################################## 986 987sub get_Destination_Directory_For_Item_From_Directorylist # this is used for Files, Profiles and Links 988{ 989 my ($itemarrayref, $dirsarrayref) = @_; 990 991 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::get_Destination_Directory_For_Item_From_Directorylist : $#{$itemarrayref} : $#{$dirsarrayref}"); } 992 993 for ( my $i = 0; $i <= $#{$itemarrayref}; $i++ ) 994 { 995 my $oneitem = ${$itemarrayref}[$i]; 996 my $oneitemgid = $oneitem->{'gid'}; 997 my $directorygid = $oneitem->{'Dir'}; # for instance gid_Dir_Program 998 my $netdirectorygid = ""; 999 my $onelanguage = $oneitem->{'specificlanguage'}; 1000 my $ispredefinedprogdir = 0; 1001 my $ispredefinedconfigdir = 0; 1002 1003 my $oneitemname = $oneitem->{'Name'}; 1004 1005 if ( $oneitem->{'NetDir'} ) { $netdirectorygid = $oneitem->{'NetDir'}; } 1006 1007 installer::pathanalyzer::make_absolute_filename_to_relative_filename(\$oneitemname); # making /registry/schema/org/openoffice/VCL.xcs to VCL.xcs 1008 1009 my $searchdirgid; 1010 1011 if ( $netdirectorygid eq "" ) # if NetDir is defined, it is privileged 1012 { 1013 $searchdirgid = $directorygid 1014 } 1015 else 1016 { 1017 $searchdirgid = $netdirectorygid 1018 } 1019 1020 if ($searchdirgid =~ /PREDEFINED_PROGDIR/) # the root directory is not defined in setup script 1021 { 1022 $ispredefinedprogdir = 1; 1023 } 1024 1025 if ($searchdirgid =~ /PREDEFINED_CONFIGDIR/) # the root directory is not defined in setup script 1026 { 1027 $ispredefinedconfigdir = 1; 1028 } 1029 1030 my $destfilename; 1031 1032 if ((!( $ispredefinedprogdir )) && (!( $ispredefinedconfigdir ))) 1033 { 1034 my $directorynameref = get_Directoryname_From_Directorygid($dirsarrayref, $searchdirgid, $onelanguage, $oneitemgid); 1035 $destfilename = $$directorynameref . $installer::globals::separator . $oneitemname; 1036 } 1037 else 1038 { 1039 $destfilename = $oneitemname; 1040 } 1041 1042 $oneitem->{'destination'} = $destfilename; 1043 } 1044} 1045 1046########################################################################## 1047# Searching a file in a list of pathes 1048########################################################################## 1049 1050sub get_sourcepath_from_filename_and_includepath_classic 1051{ 1052 my ($searchfilenameref, $includepatharrayref, $write_logfile) = @_; 1053 1054 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::get_sourcepath_from_filename_and_includepath_classic : $$searchfilenameref : $#{$includepatharrayref} : $write_logfile"); } 1055 1056 my ($onefile, $includepath, $infoline); 1057 1058 my $foundsourcefile = 0; 1059 1060 for ( my $j = 0; $j <= $#{$includepatharrayref}; $j++ ) 1061 { 1062 $includepath = ${$includepatharrayref}[$j]; 1063 installer::remover::remove_leading_and_ending_whitespaces(\$includepath); 1064 1065 $onefile = $includepath . $installer::globals::separator . $$searchfilenameref; 1066 1067 if ( -f $onefile ) 1068 { 1069 $foundsourcefile = 1; 1070 last; 1071 } 1072 } 1073 1074 if (!($foundsourcefile)) 1075 { 1076 $onefile = ""; # the sourcepath has to be empty 1077 if ( $write_logfile) 1078 { 1079 if ( $ENV{'DEFAULT_TO_ENGLISH_FOR_PACKING'} ) 1080 { 1081 $infoline = "WARNING: Source for $$searchfilenameref not found!\n"; # Important message in log file 1082 } 1083 else 1084 { 1085 $infoline = "ERROR: Source for $$searchfilenameref not found!\n"; # Important message in log file 1086 } 1087 1088 push( @installer::globals::logfileinfo, $infoline); 1089 } 1090 } 1091 else 1092 { 1093 if ( $write_logfile) 1094 { 1095 $infoline = "SUCCESS: Source for $$searchfilenameref: $onefile\n"; 1096 push( @installer::globals::logfileinfo, $infoline); 1097 } 1098 } 1099 1100 return \$onefile; 1101} 1102 1103########################################################################## 1104# Input is one file name, output the complete absolute path of this file 1105########################################################################## 1106 1107sub get_sourcepath_from_filename_and_includepath 1108{ 1109 my ($searchfilenameref, $unused, $write_logfile) = @_; 1110 1111 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::get_sourcepath_from_filename_and_includepath : $$searchfilenameref : $#{$includepatharrayref} : $write_logfile"); } 1112 1113 my ($onefile, $includepath, $infoline); 1114 1115 my $foundsourcefile = 0; 1116 my $foundnewname = 0; 1117 1118 for ( my $j = 0; $j <= $#installer::globals::allincludepathes; $j++ ) 1119 { 1120 my $allfiles = $installer::globals::allincludepathes[$j]; 1121 1122 if ( exists( $allfiles->{$$searchfilenameref} )) 1123 { 1124 $onefile = $allfiles->{'includepath'} . $installer::globals::separator . $$searchfilenameref; 1125 $foundsourcefile = 1; 1126 last; 1127 } 1128 } 1129 1130 if (!($foundsourcefile)) # testing with lowercase filename 1131 { 1132 # Attention: README01.html is copied for Windows to readme01.html, not case sensitive 1133 1134 for ( my $j = 0; $j <= $#installer::globals::allincludepathes; $j++ ) 1135 { 1136 my $allfiles = $installer::globals::allincludepathes[$j]; 1137 1138 my $newfilename = $$searchfilenameref; 1139 $newfilename =~ s/readme/README/; # special handling for readme files 1140 $newfilename =~ s/license/LICENSE/; # special handling for license files 1141 1142 if ( exists( $allfiles->{$newfilename} )) 1143 { 1144 $onefile = $allfiles->{'includepath'} . $installer::globals::separator . $newfilename; 1145 $foundsourcefile = 1; 1146 $foundnewname = 1; 1147 last; 1148 } 1149 } 1150 } 1151 1152 if (!($foundsourcefile)) 1153 { 1154 $onefile = ""; # the sourcepath has to be empty 1155 if ( $write_logfile) 1156 { 1157 if ( $ENV{'DEFAULT_TO_ENGLISH_FOR_PACKING'} ) 1158 { 1159 $infoline = "WARNING: Source for $$searchfilenameref not found!\n"; # Important message in log file 1160 } 1161 else 1162 { 1163 $infoline = "ERROR: Source for $$searchfilenameref not found!\n"; # Important message in log file 1164 } 1165 1166 push( @installer::globals::logfileinfo, $infoline); 1167 } 1168 } 1169 else 1170 { 1171 if ( $write_logfile) 1172 { 1173 if (!($foundnewname)) 1174 { 1175 $infoline = "SUCCESS: Source for $$searchfilenameref: $onefile\n"; 1176 } 1177 else 1178 { 1179 $infoline = "SUCCESS/WARNING: Special handling for $$searchfilenameref: $onefile\n"; 1180 } 1181 push( @installer::globals::logfileinfo, $infoline); 1182 } 1183 } 1184 1185 return \$onefile; 1186} 1187 1188############################################################## 1189# Determining, whether a specified directory is language 1190# dependent 1191############################################################## 1192 1193sub determine_directory_language_dependency 1194{ 1195 my($directorygid, $dirsref) = @_; 1196 1197 my $is_multilingual = 0; 1198 1199 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 1200 { 1201 my $onedir = ${$dirsref}[$i]; 1202 my $gid = $onedir->{'gid'}; 1203 1204 if ( $gid eq $directorygid ) 1205 { 1206 $is_multilingual = $onedir->{'ismultilingual'}; 1207 last; 1208 } 1209 } 1210 1211 return $is_multilingual; 1212} 1213 1214############################################################## 1215# Getting all source pathes for all files to be packed 1216# $item can be "Files" or "ScpActions" 1217############################################################## 1218 1219sub get_Source_Directory_For_Files_From_Includepathlist 1220{ 1221 my ($filesarrayref, $includepatharrayref, $dirsref, $item) = @_; 1222 1223 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::get_Source_Directory_For_Files_From_Includepathlist : $#{$filesarrayref} : $#{$includepatharrayref} : $item"); } 1224 1225 installer::logger::include_header_into_logfile("$item:"); 1226 1227 my $infoline = ""; 1228 1229 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 1230 { 1231 my $onefile = ${$filesarrayref}[$i]; 1232 my $onelanguage = $onefile->{'specificlanguage'}; 1233 1234 if ( ! $onefile->{'Name'} ) { installer::exiter::exit_program("ERROR: $item without name ! GID: $onefile->{'gid'} ! Language: $onelanguage", "get_Source_Directory_For_Files_From_Includepathlist"); } 1235 1236 my $onefilename = $onefile->{'Name'}; 1237 if ( $item eq "ScpActions" ) { $onefilename =~ s/\//$installer::globals::separator/g; } 1238 $onefilename =~ s/^\s*\Q$installer::globals::separator\E//; # filename begins with a slash, for instance /registry/schema/org/openoffice/VCL.xcs 1239 1240 my $styles = ""; 1241 my $file_can_miss = 0; 1242 if ( $onefile->{'Styles'} ) { $styles = $onefile->{'Styles'}; } 1243 if ( $styles =~ /\bFILE_CAN_MISS\b/ ) { $file_can_miss = 1; } 1244 1245 if (( $installer::globals::languagepack ) && ( ! $onefile->{'ismultilingual'} ) && ( ! ( $styles =~ /\bFORCELANGUAGEPACK\b/ ))) { $file_can_miss = 1; } 1246 1247 my $sourcepathref = ""; 1248 1249 if ( $file_can_miss ) { $sourcepathref = get_sourcepath_from_filename_and_includepath(\$onefilename, $includepatharrayref, 0); } 1250 else { $sourcepathref = get_sourcepath_from_filename_and_includepath(\$onefilename, $includepatharrayref, 1); } 1251 1252 $onefile->{'sourcepath'} = $$sourcepathref; # This $$sourcepathref is empty, if no source was found 1253 1254 # defaulting to english for multilingual files if DEFAULT_TO_ENGLISH_FOR_PACKING is set 1255 1256 if ( $ENV{'DEFAULT_TO_ENGLISH_FOR_PACKING'} ) 1257 { 1258 if (( ! $onefile->{'sourcepath'} ) && ( $onefile->{'ismultilingual'} )) 1259 { 1260 my $oldname = $onefile->{'Name'}; 1261 my $oldlanguage = $onefile->{'specificlanguage'}; 1262 my $newlanguage = "en-US"; 1263 # $onefile->{'Name'} =~ s/$oldlanguage\./$newlanguage\./; # Example: tplwizfax_it.zip -> tplwizfax_en-US.zip 1264 $onefilename = $onefile->{'Name'}; 1265 $onefilename =~ s/$oldlanguage\./$newlanguage\./; # Example: tplwizfax_it.zip -> tplwizfax_en-US.zip 1266 $onefilename =~ s/^\s*\Q$installer::globals::separator\E//; # filename begins with a slash, for instance /registry/schema/org/openoffice/VCL.xcs 1267 $sourcepathref = get_sourcepath_from_filename_and_includepath(\$onefilename, $includepatharrayref, 1); 1268 $onefile->{'sourcepath'} = $$sourcepathref; # This $$sourcepathref is empty, if no source was found 1269 1270 if ($onefile->{'sourcepath'}) # defaulting to english was successful 1271 { 1272 $infoline = "WARNING: Using $onefilename instead of $oldname\n"; 1273 push( @installer::globals::logfileinfo, $infoline); 1274 print " $infoline"; 1275 # if ( $onefile->{'destination'} ) { $onefile->{'destination'} =~ s/\Q$oldname\E/$onefile->{'Name'}/; } 1276 1277 # If the directory, in which the new file is installed, is not language dependent, 1278 # the filename has to be changed to avoid installation conflicts 1279 # No mechanism for resource files! 1280 # -> implementing for the content of ARCHIVE files 1281 1282 if ( $onefile->{'Styles'} =~ /\bARCHIVE\b/ ) 1283 { 1284 my $directorygid = $onefile->{'Dir'}; 1285 my $islanguagedependent = determine_directory_language_dependency($directorygid, $dirsref); 1286 1287 if ( ! $islanguagedependent ) 1288 { 1289 $onefile->{'Styles'} =~ s/\bARCHIVE\b/ARCHIVE, RENAME_TO_LANGUAGE/; # Setting new flag RENAME_TO_LANGUAGE 1290 $infoline = "Setting flag RENAME_TO_LANGUAGE: File $onefile->{'Name'} in directory: $directorygid\n"; 1291 push( @installer::globals::logfileinfo, $infoline); 1292 } 1293 } 1294 } 1295 else 1296 { 1297 $infoline = "WARNING: Using $onefile->{'Name'} instead of $oldname was not successful\n"; 1298 push( @installer::globals::logfileinfo, $infoline); 1299 $onefile->{'Name'} = $oldname; # Switching back to old file name 1300 } 1301 } 1302 } 1303 } 1304 1305 $infoline = "\n"; # empty line after listing of all files 1306 push( @installer::globals::logfileinfo, $infoline); 1307} 1308 1309################################################################################# 1310# Removing files, that shall not be included into languagepacks 1311# (because of rpm conflicts) 1312################################################################################# 1313 1314sub remove_Files_For_Languagepacks 1315{ 1316 my ($itemsarrayref) = @_; 1317 1318 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_Files_For_Languagepacks : $#{$filesarrayref}"); } 1319 1320 my $infoline; 1321 1322 my @newitemsarray = (); 1323 1324 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 1325 { 1326 my $oneitem = ${$itemsarrayref}[$i]; 1327 my $gid = $oneitem->{'gid'}; 1328 1329 # scp Todo: Remove asap after removal of old setup 1330 1331 if (( $gid eq "gid_File_Extra_Fontunxpsprint" ) || 1332 ( $gid eq "gid_File_Extra_Migration_Lang" )) 1333 { 1334 $infoline = "ATTENTION: Removing item $oneitem->{'gid'} from the installation set.\n"; 1335 push( @installer::globals::logfileinfo, $infoline); 1336 1337 next; 1338 } 1339 1340 push(@newitemsarray, $oneitem); 1341 } 1342 1343 return \@newitemsarray; 1344} 1345 1346################################################################################# 1347# Files, whose source directory is not found, are removed now (this is an ERROR) 1348################################################################################# 1349 1350sub remove_Files_Without_Sourcedirectory 1351{ 1352 my ($filesarrayref) = @_; 1353 1354 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_Files_Without_Sourcedirectory : $#{$filesarrayref}"); } 1355 1356 my $infoline; 1357 1358 my $error_occured = 0; 1359 my @missingfiles = (); 1360 push(@missingfiles, "ERROR: The following files could not be found: \n"); 1361 1362 my @newfilesarray = (); 1363 1364 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 1365 { 1366 my $onefile = ${$filesarrayref}[$i]; 1367 my $sourcepath = $onefile->{'sourcepath'}; 1368 1369 if ($sourcepath eq "") 1370 { 1371 my $styles = $onefile->{'Styles'}; 1372 my $filename = $onefile->{'Name'}; 1373 1374 if ( ! $installer::globals::languagepack ) 1375 { 1376 $infoline = "ERROR: Removing file $filename from file list.\n"; 1377 push( @installer::globals::logfileinfo, $infoline); 1378 1379 push(@missingfiles, "ERROR: File not found: $filename\n"); 1380 $error_occured = 1; 1381 1382 next; # removing this file from list, if sourcepath is empty 1383 } 1384 else # special case for language packs 1385 { 1386 if (( $onefile->{'ismultilingual'} ) || ( $styles =~ /\bFORCELANGUAGEPACK\b/ )) 1387 { 1388 $infoline = "ERROR: Removing file $filename from file list.\n"; 1389 push( @installer::globals::logfileinfo, $infoline); 1390 1391 push(@missingfiles, "ERROR: File not found: $filename\n"); 1392 $error_occured = 1; 1393 1394 next; # removing this file from list, if sourcepath is empty 1395 } 1396 else 1397 { 1398 $infoline = "INFO: Removing file $filename from file list. It is not language dependent.\n"; 1399 push( @installer::globals::logfileinfo, $infoline); 1400 $infoline = "INFO: It is not language dependent and can be ignored in language packs.\n"; 1401 push( @installer::globals::logfileinfo, $infoline); 1402 1403 next; # removing this file from list, if sourcepath is empty 1404 } 1405 } 1406 } 1407 1408 push(@newfilesarray, $onefile); 1409 } 1410 1411 $infoline = "\n"; 1412 push( @installer::globals::logfileinfo, $infoline); 1413 1414 if ( $error_occured ) 1415 { 1416 for ( my $i = 0; $i <= $#missingfiles; $i++ ) { print "$missingfiles[$i]"; } 1417 installer::exiter::exit_program("ERROR: Missing files", "remove_Files_Without_Sourcedirectory"); 1418 } 1419 1420 return \@newfilesarray; 1421} 1422 1423############################################################################ 1424# License and Readme files in the default language have to be installed 1425# in the directory with flag OFFICEDIRECTORY. If this is not defined 1426# they have to be installed in the installation root. 1427############################################################################ 1428 1429sub get_office_directory_gid_and_hostname 1430{ 1431 my ($dirsarrayref) = @_; 1432 1433 my $foundofficedir = 0; 1434 my $gid = ""; 1435 my $hostname = ""; 1436 1437 for ( my $i = 0; $i <= $#{$dirsarrayref}; $i++ ) 1438 { 1439 my $onedir = ${$dirsarrayref}[$i]; 1440 if ( $onedir->{'Styles'} ) 1441 { 1442 my $styles = $onedir->{'Styles'}; 1443 1444 if ( $styles =~ /\bOFFICEDIRECTORY\b/ ) 1445 { 1446 $foundofficedir = 1; 1447 $gid = $onedir->{'gid'}; 1448 $hostname = $onedir->{'HostName'}; 1449 last; 1450 } 1451 } 1452 } 1453 1454 return ($foundofficedir, $gid, $hostname); 1455} 1456 1457############################################################################ 1458# License and Readme files in the default language have to be installed 1459# in the installation root (next to the program dir). This is in scp 1460# project done by a post install basic script 1461############################################################################ 1462 1463sub add_License_Files_into_Installdir 1464{ 1465 my ($filesarrayref, $dirsarrayref, $languagesarrayref) = @_; 1466 1467 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::add_License_Files_into_Installdir : $#{$filesarrayref} : $#{$languagesarrayref}"); } 1468 1469 my $infoline; 1470 1471 my @newfilesarray = (); 1472 1473 my $defaultlanguage = installer::languages::get_default_language($languagesarrayref); 1474 1475 my ($foundofficedir, $officedirectorygid, $officedirectoryhostname) = get_office_directory_gid_and_hostname($dirsarrayref); 1476 1477 # copy all files from directory share/readme, that contain the default language in their name 1478 # without default language into the installation root. This makes the settings of the correct 1479 # file names superfluous. On the other hand this requires a dependency to the directory 1480 # share/readme 1481 1482 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 1483 { 1484 my $onefile = ${$filesarrayref}[$i]; 1485 my $destination = $onefile->{'destination'}; 1486 my $styles = ""; 1487 if ( $onefile->{'Styles'} ) { $styles = $onefile->{'Styles'}; } 1488 1489 if ( ( $destination =~ /share\Q$installer::globals::separator\Ereadme\Q$installer::globals::separator\E(\w+?)_?$defaultlanguage\.?(\w*)\s*/ ) 1490 || (( $styles =~ /\bROOTLICENSEFILE\b/ ) && ( $destination =~ /\Q$installer::globals::separator\E?(\w+?)_?$defaultlanguage\.?(\w*?)\s*$/ )) ) 1491 { 1492 my $filename = $1; 1493 my $extension = $2; 1494 1495 my $newfilename; 1496 1497 if ( $extension eq "" ) { $newfilename = $filename; } 1498 else { $newfilename = $filename . "\." . $extension; } 1499 1500 my %newfile = (); 1501 my $newfile = \%newfile; 1502 1503 installer::converter::copy_item_object($onefile, $newfile); 1504 1505 $newfile->{'gid'} = $onefile->{'gid'} . "_Copy"; 1506 $newfile->{'Name'} = $newfilename; 1507 $newfile->{'ismultilingual'} = "0"; 1508 $newfile->{'specificlanguage'} = ""; 1509 $newfile->{'haslanguagemodule'} = "0"; 1510 1511 if ( defined $newfile->{'InstallName'} ) 1512 { 1513 if ( $newfile->{'InstallName'} =~ /^\s*(.*?)_$defaultlanguage\.?(\w*?)\s*$/ ) 1514 { 1515 my $localfilename = $1; 1516 my $localextension = $2; 1517 1518 if ( $localextension eq "" ) { $newfile->{'InstallName'} = $localfilename; } 1519 else { $newfile->{'InstallName'} = $localfilename . "\." . $localextension; } 1520 } 1521 } 1522 1523 $newfile->{'removelangfromfile'} = "1"; # Important for files with an InstallName, because language also has to be removed there. 1524 1525 if ( $foundofficedir ) 1526 { 1527 $newfile->{'Dir'} = $officedirectorygid; 1528 $newfile->{'destination'} = $officedirectoryhostname . $installer::globals::separator . $newfilename; 1529 } 1530 else 1531 { 1532 $newfile->{'Dir'} = "PREDEFINED_PROGDIR"; 1533 $newfile->{'destination'} = $newfilename; 1534 } 1535 1536 # Also setting "modules=gid_Module_Root_Brand" (module with style: ROOT_BRAND_PACKAGE) 1537 if ( $installer::globals::rootbrandpackageset ) 1538 { 1539 $newfile->{'modules'} = $installer::globals::rootbrandpackage; 1540 } 1541 1542 push(@newfilesarray, $newfile); 1543 1544 $infoline = "New files: Adding file $newfilename for the installation root to the file list. Language: $defaultlanguage\n"; 1545 push( @installer::globals::logfileinfo, $infoline); 1546 1547 if ( defined $newfile->{'InstallName'} ) 1548 { 1549 $infoline = "New files: Using installation name: $newfile->{'InstallName'}\n"; 1550 push( @installer::globals::logfileinfo, $infoline); 1551 } 1552 1553 # Collecting license and readme file for the installation set 1554 1555 push(@installer::globals::installsetfiles, $newfile); 1556 $infoline = "New files: Adding file $newfilename to the file collector for the installation set. Language: $defaultlanguage\n"; 1557 push( @installer::globals::logfileinfo, $infoline); 1558 } 1559 1560 push(@newfilesarray, $onefile); 1561 } 1562 1563 return \@newfilesarray; 1564} 1565 1566############################################################################ 1567# Removing files with flag ONLY_ASIA_LANGUAGE, only if no asian 1568# language is part of the product. 1569# This special files are connected to the root module and are not 1570# included into a language pack (would lead to conflicts!). 1571# But this files shall only be included into the product, if the 1572# product contains at least one asian language. 1573############################################################################ 1574 1575sub remove_onlyasialanguage_files_from_productlists 1576{ 1577 my ($filesarrayref) = @_; 1578 1579 my $infoline; 1580 1581 my @newfilesarray = (); 1582 my $returnfilesarrayref; 1583 1584 my $containsasianlanguage = installer::languages::detect_asian_language($installer::globals::alllanguagesinproductarrayref); 1585 1586 my $alllangstring = installer::converter::convert_array_to_comma_separated_string($installer::globals::alllanguagesinproductarrayref); 1587 $infoline = "\nLanguages in complete product: $alllangstring\n"; 1588 push( @installer::globals::logfileinfo, $infoline); 1589 1590 if ( ! $containsasianlanguage ) 1591 { 1592 $infoline = "Product does not contain asian language -> removing files\n"; 1593 push( @installer::globals::logfileinfo, $infoline); 1594 1595 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 1596 { 1597 my $onefile = ${$filesarrayref}[$i]; 1598 my $styles = ""; 1599 if ( $onefile->{'Styles'} ) { $styles = $onefile->{'Styles'}; } 1600 if ( $styles =~ /\bONLY_ASIA_LANGUAGE\b/ ) 1601 { 1602 $infoline = "Flag ONLY_ASIA_LANGUAGE: Removing file $onefile->{'Name'} from files collector!\n"; 1603 push( @installer::globals::logfileinfo, $infoline); 1604 next; 1605 } 1606 1607 push(@newfilesarray, $onefile); 1608 } 1609 1610 $returnfilesarrayref = \@newfilesarray; 1611 } 1612 else 1613 { 1614 $returnfilesarrayref = $filesarrayref; 1615 1616 $infoline = "Product contains asian language -> Nothing to do\n"; 1617 push( @installer::globals::logfileinfo, $infoline); 1618 1619 } 1620 1621 return $returnfilesarrayref; 1622} 1623 1624############################################################################ 1625# Removing files with flag ONLY_WESTERN_LANGUAGE, only if no western 1626# language is part of the product. 1627# This special files are connected to the root module and are not 1628# included into a language pack (would lead to conflicts!). 1629# But this files shall only be included into the product, if the 1630# product contains at least one western language. 1631############################################################################ 1632 1633sub remove_onlywesternlanguage_files_from_productlists 1634{ 1635 my ($filesarrayref) = @_; 1636 1637 my $infoline; 1638 1639 my @newfilesarray = (); 1640 my $returnfilesarrayref; 1641 1642 my $containswesternlanguage = installer::languages::detect_western_language($installer::globals::alllanguagesinproductarrayref); 1643 1644 my $alllangstring = installer::converter::convert_array_to_comma_separated_string($installer::globals::alllanguagesinproductarrayref); 1645 $infoline = "\nLanguages in complete product: $alllangstring\n"; 1646 push( @installer::globals::logfileinfo, $infoline); 1647 1648 if ( ! $containswesternlanguage ) 1649 { 1650 $infoline = "Product does not contain western language -> removing files\n"; 1651 push( @installer::globals::logfileinfo, $infoline); 1652 1653 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 1654 { 1655 my $onefile = ${$filesarrayref}[$i]; 1656 my $styles = ""; 1657 if ( $onefile->{'Styles'} ) { $styles = $onefile->{'Styles'}; } 1658 if ( $styles =~ /\bONLY_WESTERN_LANGUAGE\b/ ) 1659 { 1660 $infoline = "Flag ONLY_WESTERN_LANGUAGE: Removing file $onefile->{'Name'} from files collector!\n"; 1661 push( @installer::globals::logfileinfo, $infoline); 1662 next; 1663 } 1664 1665 push(@newfilesarray, $onefile); 1666 } 1667 1668 $returnfilesarrayref = \@newfilesarray; 1669 } 1670 else 1671 { 1672 $returnfilesarrayref = $filesarrayref; 1673 1674 $infoline = "Product contains western language -> Nothing to do\n"; 1675 push( @installer::globals::logfileinfo, $infoline); 1676 1677 } 1678 1679 return $returnfilesarrayref; 1680} 1681 1682############################################################################ 1683# Some files are included for more than one language and have the same 1684# name and the same destination directory for all languages. This would 1685# lead to conflicts, if the filenames are not changed. 1686# In scp project this files must have the flag MAKE_LANG_SPECIFIC 1687# For this files, the language is included into the filename. 1688############################################################################ 1689 1690sub make_filename_language_specific 1691{ 1692 my ($filesarrayref) = @_; 1693 1694 my $infoline = ""; 1695 1696 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 1697 { 1698 my $onefile = ${$filesarrayref}[$i]; 1699 1700 if ( $onefile->{'ismultilingual'} ) 1701 { 1702 my $styles = ""; 1703 if ( $onefile->{'Styles'} ) { $styles = $onefile->{'Styles'}; } 1704 if ( $styles =~ /\bMAKE_LANG_SPECIFIC\b/ ) 1705 { 1706 my $language = $onefile->{'specificlanguage'}; 1707 my $olddestination = $onefile->{'destination'}; 1708 my $oldname = $onefile->{'Name'}; 1709 1710 # Including the language into the file name. 1711 # But be sure, to include the language before the file extension. 1712 1713 my $fileextension = ""; 1714 1715 if ( $onefile->{'Name'} =~ /(\.\w+?)\s*$/ ) { $fileextension = $1; } 1716 if ( $fileextension ne "" ) 1717 { 1718 $onefile->{'Name'} =~ s/\Q$fileextension\E\s*$/_$language$fileextension/; 1719 $onefile->{'destination'} =~ s/\Q$fileextension\E\s*$/_$language$fileextension/; 1720 } 1721 1722 $infoline = "Flag MAKE_LANG_SPECIFIC:\n"; 1723 push( @installer::globals::logfileinfo, $infoline); 1724 $infoline = "Changing name from $oldname to $onefile->{'Name'} !\n"; 1725 push( @installer::globals::logfileinfo, $infoline); 1726 $infoline = "Changing destination from $olddestination to $onefile->{'destination'} !\n"; 1727 push( @installer::globals::logfileinfo, $infoline); 1728 } 1729 } 1730 } 1731} 1732 1733############################################################################ 1734# Removing all scpactions, that have no name. 1735# See: FlatLoaderZip 1736############################################################################ 1737 1738sub remove_scpactions_without_name 1739{ 1740 my ($itemsarrayref) = @_; 1741 1742 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_scpactions_without_name : $#{$itemsarrayref}"); } 1743 1744 my $infoline; 1745 1746 my @newitemsarray = (); 1747 1748 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 1749 { 1750 my $oneitem = ${$itemsarrayref}[$i]; 1751 my $name = ""; 1752 1753 if ( $oneitem->{'Name'} ) { $name = $oneitem->{'Name'}; } 1754 1755 if ( $name eq "" ) 1756 { 1757 $infoline = "ATTENTION: Removing scpaction $oneitem->{'gid'} from the installation set.\n"; 1758 push( @installer::globals::logfileinfo, $infoline); 1759 next; 1760 } 1761 1762 push(@newitemsarray, $oneitem); 1763 } 1764 1765 return \@newitemsarray; 1766} 1767 1768############################################################################ 1769# Because of the item "File" the source name must be "Name". Therefore 1770# "Copy" is changed to "Name" and "Name" is changed to "DestinationName". 1771############################################################################ 1772 1773sub change_keys_of_scpactions 1774{ 1775 my ($itemsarrayref) = @_; 1776 1777 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::change_keys_of_scpactions : $#{$itemsarrayref}"); } 1778 1779 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 1780 { 1781 my $oneitem = ${$itemsarrayref}[$i]; 1782 1783 my $key; 1784 1785 # First Name to DestinationName, then deleting Name 1786 foreach $key (keys %{$oneitem}) 1787 { 1788 if ( $key =~ /\bName\b/ ) 1789 { 1790 my $value = $oneitem->{$key}; 1791 my $oldkey = $key; 1792 $key =~ s/Name/DestinationName/; 1793 $oneitem->{$key} = $value; 1794 delete($oneitem->{$oldkey}); 1795 } 1796 } 1797 1798 # Second Copy to Name, then deleting Copy 1799 foreach $key (keys %{$oneitem}) 1800 { 1801 if ( $key =~ /\bCopy\b/ ) 1802 { 1803 my $value = $oneitem->{$key}; 1804 my $oldkey = $key; 1805 $key =~ s/Copy/Name/; 1806 $oneitem->{$key} = $value; 1807 delete($oneitem->{$oldkey}); 1808 } 1809 } 1810 } 1811} 1812 1813############################################################################ 1814# Removing all xpd only items from installation set (scpactions with 1815# the style XPD_ONLY), except an xpd installation set is created 1816############################################################################ 1817 1818sub remove_Xpdonly_Items 1819{ 1820 my ($itemsarrayref) = @_; 1821 1822 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_Xpdonly_Items : $#{$itemsarrayref}"); } 1823 1824 my $infoline; 1825 1826 my @newitemsarray = (); 1827 1828 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 1829 { 1830 my $oneitem = ${$itemsarrayref}[$i]; 1831 my $styles = ""; 1832 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 1833 1834 if ( $styles =~ /\bXPD_ONLY\b/ ) 1835 { 1836 $infoline = "Removing \"xpd only\" item $oneitem->{'gid'} from the installation set.\n"; 1837 push( @installer::globals::globallogfileinfo, $infoline); 1838 1839 next; 1840 } 1841 1842 push(@newitemsarray, $oneitem); 1843 } 1844 1845 $infoline = "\n"; 1846 push( @installer::globals::globallogfileinfo, $infoline); 1847 1848 return \@newitemsarray; 1849} 1850 1851############################################################################ 1852# Removing all language pack files from installation set (files with 1853# the style LANGUAGEPACK), except this is a language pack. 1854############################################################################ 1855 1856sub remove_Languagepacklibraries_from_Installset 1857{ 1858 my ($itemsarrayref) = @_; 1859 1860 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_Languagepacklibraries_from_Installset : $#{$itemsarrayref}"); } 1861 1862 my $infoline; 1863 1864 my @newitemsarray = (); 1865 1866 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 1867 { 1868 my $oneitem = ${$itemsarrayref}[$i]; 1869 my $styles = ""; 1870 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 1871 1872 if ( $styles =~ /\bLANGUAGEPACK\b/ ) 1873 { 1874 $infoline = "Removing language pack file $oneitem->{'gid'} from the installation set.\n"; 1875 push( @installer::globals::globallogfileinfo, $infoline); 1876 1877 next; 1878 } 1879 1880 push(@newitemsarray, $oneitem); 1881 } 1882 1883 $infoline = "\n"; 1884 push( @installer::globals::globallogfileinfo, $infoline); 1885 1886 return \@newitemsarray; 1887} 1888 1889############################################################################ 1890# Removing all files with flag PATCH_ONLY from installation set. 1891# This function is not called during patch creation. 1892############################################################################ 1893 1894sub remove_patchonlyfiles_from_Installset 1895{ 1896 my ($itemsarrayref) = @_; 1897 1898 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_patchonlyfiles_from_Installset : $#{$itemsarrayref}"); } 1899 1900 my $infoline; 1901 1902 my @newitemsarray = (); 1903 1904 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 1905 { 1906 my $oneitem = ${$itemsarrayref}[$i]; 1907 my $styles = ""; 1908 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 1909 1910 if ( $styles =~ /\bPATCH_ONLY\b/ ) 1911 { 1912 $infoline = "Removing file with flag PATCH_ONLY $oneitem->{'gid'} from the installation set.\n"; 1913 push( @installer::globals::globallogfileinfo, $infoline); 1914 1915 next; 1916 } 1917 1918 push(@newitemsarray, $oneitem); 1919 } 1920 1921 $infoline = "\n"; 1922 push( @installer::globals::globallogfileinfo, $infoline); 1923 1924 return \@newitemsarray; 1925} 1926 1927############################################################################ 1928# Removing all files with flag TAB_ONLY from installation set. 1929# This function is not called during tab creation. 1930############################################################################ 1931 1932sub remove_tabonlyfiles_from_Installset 1933{ 1934 my ($itemsarrayref) = @_; 1935 1936 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_tabonlyfiles_from_Installset : $#{$itemsarrayref}"); } 1937 1938 my $infoline; 1939 1940 my @newitemsarray = (); 1941 1942 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 1943 { 1944 my $oneitem = ${$itemsarrayref}[$i]; 1945 my $styles = ""; 1946 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 1947 1948 if ( $styles =~ /\bTAB_ONLY\b/ ) 1949 { 1950 $infoline = "Removing tab only file $oneitem->{'gid'} from the installation set.\n"; 1951 push( @installer::globals::globallogfileinfo, $infoline); 1952 1953 next; 1954 } 1955 1956 push(@newitemsarray, $oneitem); 1957 } 1958 1959 $infoline = "\n"; 1960 push( @installer::globals::globallogfileinfo, $infoline); 1961 1962 return \@newitemsarray; 1963} 1964 1965############################################################################### 1966# Removing all files with flag ONLY_INSTALLED_PRODUCT from installation set. 1967# This function is not called for PKGFORMAT installed and archive. 1968############################################################################### 1969 1970sub remove_installedproductonlyfiles_from_Installset 1971{ 1972 my ($itemsarrayref) = @_; 1973 1974 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_installedproductonlyfiles_from_Installset : $#{$itemsarrayref}"); } 1975 1976 my $infoline; 1977 1978 my @newitemsarray = (); 1979 1980 for ( my $i = 0; $i <= $#{$itemsarrayref}; $i++ ) 1981 { 1982 my $oneitem = ${$itemsarrayref}[$i]; 1983 my $styles = ""; 1984 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 1985 1986 if ( $styles =~ /\bONLY_INSTALLED_PRODUCT\b/ ) 1987 { 1988 $infoline = "Removing file $oneitem->{'gid'} from the installation set. This file is only required for PKGFORMAT archive or installed).\n"; 1989 push( @installer::globals::globallogfileinfo, $infoline); 1990 next; 1991 } 1992 1993 push(@newitemsarray, $oneitem); 1994 } 1995 1996 $infoline = "\n"; 1997 push( @installer::globals::globallogfileinfo, $infoline); 1998 1999 return \@newitemsarray; 2000} 2001 2002############################################################################ 2003# Some files cotain a $ in their name. epm conflicts with such files. 2004# Solution: Renaming this files, converting "$" to "$$" 2005############################################################################ 2006 2007sub quoting_illegal_filenames 2008{ 2009 my ($filesarrayref) = @_; 2010 2011 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::rename_illegal_filenames : $#{$filesarrayref}"); } 2012 2013 # This function has to be removed as soon as possible! 2014 2015 installer::logger::include_header_into_logfile("Renaming illegal filenames:"); 2016 2017 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 2018 { 2019 my $onefile = ${$filesarrayref}[$i]; 2020 my $filename = $onefile->{'Name'}; 2021 2022 if ( $filename =~ /\$/ ) 2023 { 2024 my $sourcepath = $onefile->{'sourcepath'}; 2025 my $destpath = $onefile->{'destination'}; 2026 2027 # sourcepath and destination have to be quoted for epm list file 2028 2029 # $filename =~ s/\$/\$\$/g; 2030 $destpath =~ s/\$/\$\$/g; 2031 $sourcepath =~ s/\$/\$\$/g; 2032 2033 # my $infoline = "ATTENTION: Files: Renaming $onefile->{'Name'} to $filename\n"; 2034 # push( @installer::globals::logfileinfo, $infoline); 2035 my $infoline = "ATTENTION: Files: Quoting sourcepath $onefile->{'sourcepath'} to $sourcepath\n"; 2036 push( @installer::globals::logfileinfo, $infoline); 2037 $infoline = "ATTENTION: Files: Quoting destination path $onefile->{'destination'} to $destpath\n"; 2038 push( @installer::globals::logfileinfo, $infoline); 2039 2040 # $onefile->{'Name'} = $filename; 2041 $onefile->{'sourcepath'} = $sourcepath; 2042 $onefile->{'destination'} = $destpath; 2043 } 2044 } 2045} 2046 2047############################################################################ 2048# Removing multiple occurences of same module. 2049############################################################################ 2050 2051sub optimize_list 2052{ 2053 my ( $longlist ) = @_; 2054 2055 my $shortlist = ""; 2056 my $hashref = installer::converter::convert_stringlist_into_hash(\$longlist, ","); 2057 foreach my $key (sort keys %{$hashref} ) { $shortlist = "$shortlist,$key"; } 2058 $shortlist =~ s/^\s*\,//; 2059 2060 return $shortlist; 2061} 2062 2063####################################################################### 2064# Collecting all directories needed for the epm list 2065# 1. Looking for all destination paths in the files array 2066# 2. Looking for directories with CREATE flag in the directory array 2067####################################################################### 2068 2069################################## 2070# Collecting directories: Part 1 2071################################## 2072 2073sub collect_directories_from_filesarray 2074{ 2075 my ($filesarrayref) = @_; 2076 2077 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::collect_directories_from_filesarray : $#{$filesarrayref}"); } 2078 2079 my @alldirectories = (); 2080 my %alldirectoryhash = (); 2081 2082 my $predefinedprogdir_added = 0; 2083 my $alreadyincluded = 0; 2084 2085 # Preparing this already as hash, although the only needed value at the moment is the HostName 2086 # But also adding: "specificlanguage" and "Dir" (for instance gid_Dir_Program) 2087 2088 for ( my $i = 0; $i <= $#{$filesarrayref}; $i++ ) 2089 { 2090 my $onefile = ${$filesarrayref}[$i]; 2091 my $destinationpath = $onefile->{'destination'}; 2092 installer::pathanalyzer::get_path_from_fullqualifiedname(\$destinationpath); 2093 $destinationpath =~ s/\Q$installer::globals::separator\E\s*$//; # removing ending slashes or backslashes 2094 2095 $alreadyincluded = 0; 2096 if ( exists($alldirectoryhash{$destinationpath}) ) { $alreadyincluded = 1; } 2097 2098 if (!($alreadyincluded)) 2099 { 2100 my %directoryhash = (); 2101 $directoryhash{'HostName'} = $destinationpath; 2102 $directoryhash{'specificlanguage'} = $onefile->{'specificlanguage'}; 2103 $directoryhash{'Dir'} = $onefile->{'Dir'}; 2104 $directoryhash{'modules'} = $onefile->{'modules'}; # NEW, saving modules 2105 # NEVER!!! if ( ! $installer::globals::iswindowsbuild ) { $directoryhash{'Styles'} = "(CREATE)"; } # this directories must be created 2106 2107 if ( $onefile->{'Dir'} eq "PREDEFINED_PROGDIR" ) { $predefinedprogdir_added = 1; } 2108 2109 $alldirectoryhash{$destinationpath} = \%directoryhash; 2110 2111 # Problem: The $destinationpath can be share/registry/schema/org/openoffice 2112 # but not all directories contain files and will be added to this list. 2113 # Therefore the path has to be analyzed. 2114 2115 while ( $destinationpath =~ /(^.*\S)\Q$installer::globals::separator\E(\S.*?)\s*$/ ) # as long as the path contains slashes 2116 { 2117 $destinationpath = $1; 2118 2119 $alreadyincluded = 0; 2120 if ( exists($alldirectoryhash{$destinationpath}) ) { $alreadyincluded = 1; } 2121 2122 if (!($alreadyincluded)) 2123 { 2124 my %directoryhash = (); 2125 2126 $directoryhash{'HostName'} = $destinationpath; 2127 $directoryhash{'specificlanguage'} = $onefile->{'specificlanguage'}; 2128 $directoryhash{'Dir'} = $onefile->{'Dir'}; 2129 $directoryhash{'modules'} = $onefile->{'modules'}; # NEW, saving modules 2130 # NEVER!!! if ( ! $installer::globals::iswindowsbuild ) { $directoryhash{'Styles'} = "(CREATE)"; } # this directories must be created 2131 2132 $alldirectoryhash{$destinationpath} = \%directoryhash; 2133 } 2134 else 2135 { 2136 # Adding the modules to the module list! 2137 $alldirectoryhash{$destinationpath}->{'modules'} = $alldirectoryhash{$destinationpath}->{'modules'} . "," . $onefile->{'modules'}; 2138 } 2139 } 2140 } 2141 else 2142 { 2143 # Adding the modules to the module list! 2144 $alldirectoryhash{$destinationpath}->{'modules'} = $alldirectoryhash{$destinationpath}->{'modules'} . "," . $onefile->{'modules'}; 2145 2146 # Also adding the module to all parents 2147 while ( $destinationpath =~ /(^.*\S)\Q$installer::globals::separator\E(\S.*?)\s*$/ ) # as long as the path contains slashes 2148 { 2149 $destinationpath = $1; 2150 $alldirectoryhash{$destinationpath}->{'modules'} = $alldirectoryhash{$destinationpath}->{'modules'} . "," . $onefile->{'modules'}; 2151 } 2152 } 2153 } 2154 2155 # if there is no file in the root directory PREDEFINED_PROGDIR, it has to be included into the directory array now 2156 # HostName= specificlanguage= Dir=PREDEFINED_PROGDIR 2157 2158 if (! $predefinedprogdir_added ) 2159 { 2160 my %directoryhash = (); 2161 $directoryhash{'HostName'} = ""; 2162 $directoryhash{'specificlanguage'} = ""; 2163 $directoryhash{'modules'} = ""; # ToDo? 2164 $directoryhash{'Dir'} = "PREDEFINED_PROGDIR"; 2165 2166 push(@alldirectories, \%directoryhash); 2167 } 2168 2169 # Creating directory array 2170 foreach my $destdir ( sort keys %alldirectoryhash ) 2171 { 2172 $alldirectoryhash{$destdir}->{'modules'} = optimize_list($alldirectoryhash{$destdir}->{'modules'}); 2173 push(@alldirectories, $alldirectoryhash{$destdir}); 2174 } 2175 2176 return (\@alldirectories, \%alldirectoryhash); 2177} 2178 2179################################## 2180# Collecting directories: Part 2 2181################################## 2182 2183sub collect_directories_with_create_flag_from_directoryarray 2184{ 2185 my ($directoryarrayref, $alldirectoryhash) = @_; 2186 2187 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::collect_directories_with_create_flag_from_directoryarray : $#{$directoryarrayref}"); } 2188 2189 my $alreadyincluded = 0; 2190 my @alldirectories = (); 2191 2192 for ( my $i = 0; $i <= $#{$directoryarrayref}; $i++ ) 2193 { 2194 my $onedir = ${$directoryarrayref}[$i]; 2195 my $styles = ""; 2196 $newdirincluded = 0; 2197 2198 if ( $onedir->{'Styles'} ) { $styles = $onedir->{'Styles'}; } 2199 2200 if ( $styles =~ /\bCREATE\b/ ) 2201 { 2202 my $directoryname = ""; 2203 2204 if ( $onedir->{'HostName'} ) { $directoryname = $onedir->{'HostName'}; } 2205 else { installer::exiter::exit_program("ERROR: No directory name (HostName) set for specified language in gid $onedir->{'gid'}", "collect_directories_with_create_flag_from_directoryarray"); } 2206 2207 $alreadyincluded = 0; 2208 if ( exists($alldirectoryhash->{$directoryname}) ) { $alreadyincluded = 1; } 2209 2210 if (!($alreadyincluded)) 2211 { 2212 my %directoryhash = (); 2213 $directoryhash{'HostName'} = $directoryname; 2214 $directoryhash{'specificlanguage'} = $onedir->{'specificlanguage'}; 2215 # $directoryhash{'gid'} = $onedir->{'gid'}; 2216 $directoryhash{'Dir'} = $onedir->{'gid'}; 2217 $directoryhash{'Styles'} = $onedir->{'Styles'}; 2218 2219 # saving also the modules 2220 if ( ! $onedir->{'modules'} ) { installer::exiter::exit_program("ERROR: No assigned modules found for directory $onedir->{'gid'}", "collect_directories_with_create_flag_from_directoryarray"); } 2221 $directoryhash{'modules'} = $onedir->{'modules'}; 2222 2223 $alldirectoryhash->{$directoryname} = \%directoryhash; 2224 $newdirincluded = 1; 2225 2226 # Problem: The $destinationpath can be share/registry/schema/org/openoffice 2227 # but not all directories contain files and will be added to this list. 2228 # Therefore the path has to be analyzed. 2229 2230 while ( $directoryname =~ /(^.*\S)\Q$installer::globals::separator\E(\S.*?)\s*$/ ) # as long as the path contains slashes 2231 { 2232 $directoryname = $1; 2233 2234 $alreadyincluded = 0; 2235 if ( exists($alldirectoryhash->{$directoryname}) ) { $alreadyincluded = 1; } 2236 2237 if (!($alreadyincluded)) 2238 { 2239 my %directoryhash = (); 2240 2241 $directoryhash{'HostName'} = $directoryname; 2242 $directoryhash{'specificlanguage'} = $onedir->{'specificlanguage'}; 2243 $directoryhash{'Dir'} = $onedir->{'gid'}; 2244 if ( ! $installer::globals::iswindowsbuild ) { $directoryhash{'Styles'} = "(CREATE)"; } # Exeception for Windows? 2245 2246 # saving also the modules 2247 $directoryhash{'modules'} = $onedir->{'modules'}; 2248 2249 $alldirectoryhash->{$directoryname} = \%directoryhash; 2250 $newdirincluded = 1; 2251 } 2252 else 2253 { 2254 # Adding the modules to the module list! 2255 $alldirectoryhash->{$directoryname}->{'modules'} = $alldirectoryhash->{$directoryname}->{'modules'} . "," . $onedir->{'modules'}; 2256 } 2257 } 2258 } 2259 else 2260 { 2261 # Adding the modules to the module list! 2262 $alldirectoryhash->{$directoryname}->{'modules'} = $alldirectoryhash->{$directoryname}->{'modules'} . "," . $onedir->{'modules'}; 2263 2264 while ( $directoryname =~ /(^.*\S)\Q$installer::globals::separator\E(\S.*?)\s*$/ ) # as long as the path contains slashes 2265 { 2266 $directoryname = $1; 2267 # Adding the modules to the module list! 2268 $alldirectoryhash->{$directoryname}->{'modules'} = $alldirectoryhash->{$directoryname}->{'modules'} . "," . $onedir->{'modules'}; 2269 } 2270 } 2271 } 2272 2273 # Saving the styles for already added directories in function collect_directories_from_filesarray 2274 2275 if (( ! $newdirincluded ) && ( $styles ne "" )) 2276 { 2277 $styles =~ s/\bWORKSTATION\b//; 2278 $styles =~ s/\bCREATE\b//; 2279 2280 if (( ! ( $styles =~ /^\s*\(\s*\)\s*$/ )) && ( ! ( $styles =~ /^\s*\(\s*\,\s*\)\s*$/ )) && ( ! ( $styles =~ /^\s*$/ ))) # checking, if there are styles left 2281 { 2282 my $directoryname = ""; 2283 if ( $onedir->{'HostName'} ) { $directoryname = $onedir->{'HostName'}; } 2284 else { installer::exiter::exit_program("ERROR: No directory name (HostName) set for specified language in gid $onedir->{'gid'}", "collect_directories_with_create_flag_from_directoryarray"); } 2285 2286 if ( exists($alldirectoryhash->{$directoryname}) ) 2287 { 2288 $alldirectoryhash->{$directoryname}->{'Styles'} = $styles; 2289 } 2290 } 2291 } 2292 } 2293 2294 # Creating directory array 2295 foreach my $destdir ( sort keys %{$alldirectoryhash} ) 2296 { 2297 $alldirectoryhash->{$destdir}->{'modules'} = optimize_list($alldirectoryhash->{$destdir}->{'modules'}); 2298 push(@alldirectories, $alldirectoryhash->{$destdir}); 2299 } 2300 2301 return (\@alldirectories, \%alldirectoryhash); 2302} 2303 2304################################################# 2305# Determining the destination file of a link 2306################################################# 2307 2308sub get_destination_file_path_for_links 2309{ 2310 my ($linksarrayref, $filesarrayref) = @_; 2311 2312 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::get_destination_file_path_for_links : $#{$linksarrayref} : $#{$filesarrayref}"); } 2313 2314 my $infoline; 2315 2316 for ( my $i = 0; $i <= $#{$linksarrayref}; $i++ ) 2317 { 2318 my $fileid = ""; 2319 my $onelink = ${$linksarrayref}[$i]; 2320 if ( $onelink->{'FileID'} ) { $fileid = $onelink->{'FileID'}; } 2321 2322 if (!( $fileid eq "" )) 2323 { 2324 my $foundfile = 0; 2325 2326 for ( my $j = 0; $j <= $#{$filesarrayref}; $j++ ) 2327 { 2328 my $onefile = ${$filesarrayref}[$j]; 2329 my $filegid = $onefile->{'gid'}; 2330 2331 if ( $filegid eq $fileid ) 2332 { 2333 $foundfile = 1; 2334 $onelink->{'destinationfile'} = $onefile->{'destination'}; 2335 last; 2336 } 2337 } 2338 2339 if (!($foundfile)) 2340 { 2341 $infoline = "Warning: FileID $fileid for Link $onelink->{'gid'} not found!\n"; 2342 push( @installer::globals::logfileinfo, $infoline); 2343 } 2344 } 2345 } 2346 2347 $infoline = "\n"; 2348 push( @installer::globals::logfileinfo, $infoline); 2349} 2350 2351################################################# 2352# Determining the destination link of a link 2353################################################# 2354 2355sub get_destination_link_path_for_links 2356{ 2357 my ($linksarrayref) = @_; 2358 2359 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::get_destination_link_path_for_links : $#{$linksarrayref}"); } 2360 2361 my $infoline; 2362 2363 for ( my $i = 0; $i <= $#{$linksarrayref}; $i++ ) 2364 { 2365 my $shortcutid = ""; 2366 my $onelink = ${$linksarrayref}[$i]; 2367 if ( $onelink->{'ShortcutID'} ) { $shortcutid = $onelink->{'ShortcutID'}; } 2368 2369 if (!( $shortcutid eq "" )) 2370 { 2371 my $foundlink = 0; 2372 2373 for ( my $j = 0; $j <= $#{$linksarrayref}; $j++ ) 2374 { 2375 my $destlink = ${$linksarrayref}[$j]; 2376 $shortcutgid = $destlink->{'gid'}; 2377 2378 if ( $shortcutgid eq $shortcutid ) 2379 { 2380 $foundlink = 1; 2381 $onelink->{'destinationfile'} = $destlink->{'destination'}; # making key 'destinationfile' 2382 last; 2383 } 2384 } 2385 2386 if (!($foundlink)) 2387 { 2388 $infoline = "Warning: ShortcutID $shortcutid for Link $onelink->{'gid'} not found!\n"; 2389 push( @installer::globals::logfileinfo, $infoline); 2390 } 2391 } 2392 } 2393 2394 $infoline = "\n"; 2395 push( @installer::globals::logfileinfo, $infoline); 2396} 2397 2398################################################################################### 2399# Items with flag WORKSTATION are not needed (here: links and configurationitems) 2400################################################################################### 2401 2402sub remove_workstation_only_items 2403{ 2404 my ($itemarrayref) = @_; 2405 2406 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::remove_workstation_only_items : $#{$itemarrayref}"); } 2407 2408 my @newitemarray = (); 2409 2410 for ( my $i = 0; $i <= $#{$itemarrayref}; $i++ ) 2411 { 2412 my $oneitem = ${$itemarrayref}[$i]; 2413 my $styles = $oneitem->{'Styles'}; 2414 2415 if (( $styles =~ /\bWORKSTATION\b/ ) && 2416 (!( $styles =~ /\bNETWORK\b/ )) && 2417 (!( $styles =~ /\bSTANDALONE\b/ ))) 2418 { 2419 next; # removing this link, it is only needed for a workstation installation 2420 } 2421 2422 push(@newitemarray, $oneitem); 2423 } 2424 2425 return \@newitemarray; 2426} 2427 2428################################################ 2429# Resolving relative path in links 2430################################################ 2431 2432sub resolve_links_with_flag_relative 2433{ 2434 my ($linksarrayref) = @_; 2435 2436 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::resolve_links_with_flag_relative : $#{$linksarrayref}"); } 2437 2438 # Before this step is: 2439 # destination=program/libsalhelperC52.so.3, this will be the name of the link 2440 # destinationfile=program/libsalhelperC52.so.3, this will be the linked file or name 2441 # If the flag RELATIVE is set, the pathes have to be analyzed. If the flag is not set 2442 # (this will not occur in the future?) destinationfile has to be an absolute path name 2443 2444 for ( my $i = 0; $i <= $#{$linksarrayref}; $i++ ) 2445 { 2446 my $onelink = ${$linksarrayref}[$i]; 2447 my $styles = $onelink->{'Styles'}; 2448 2449 if ( $styles =~ /\bRELATIVE\b/ ) 2450 { 2451 # ToDo: This is only a simple not sufficient mechanism 2452 2453 my $destination = $onelink->{'destination'}; 2454 my $destinationfile = $onelink->{'destinationfile'}; 2455 2456 my $destinationpath = $destination; 2457 2458 installer::pathanalyzer::get_path_from_fullqualifiedname(\$destinationpath); 2459 2460 my $destinationfilepath = $destinationfile; 2461 2462 # it is possible, that the destinationfile is no longer part of the files collector 2463 if ($destinationfilepath) { installer::pathanalyzer::get_path_from_fullqualifiedname(\$destinationfilepath); } 2464 else { $destinationfilepath = ""; } 2465 2466 if ( $destinationpath eq $destinationfilepath ) 2467 { 2468 # link and file are in the same directory 2469 # Therefore the path of the file can be removed 2470 2471 my $newdestinationfile = $destinationfile; 2472 installer::pathanalyzer::make_absolute_filename_to_relative_filename(\$newdestinationfile); 2473 2474 $onelink->{'destinationfile'} = $newdestinationfile; 2475 } 2476 } 2477 } 2478} 2479 2480######################################################################## 2481# This function is a helper of function "assigning_modules_to_items" 2482######################################################################## 2483 2484sub insert_for_item ($$$) 2485{ 2486 my ($hash, $item, $id) = @_; 2487 2488 # print STDERR "insert '$id' for '$item'\n"; 2489 if (!defined $hash->{$item}) 2490 { 2491 my @gids = (); 2492 $hash->{$item} = \@gids; 2493 } 2494 my $gid_list = $hash->{$item}; 2495 push @{$gid_list}, $id; 2496 $hash->{$item} = $gid_list; 2497} 2498 2499sub build_modulegids_table 2500{ 2501 my ($modulesref, $itemname) = @_; 2502 2503 my %module_lookup_table = (); 2504 2505 # build map of item names to list of respective module gids 2506 # containing these items 2507 for my $onemodule (@{$modulesref}) 2508 { 2509 next if ( ! defined $onemodule->{$itemname} ); 2510 # these are the items contained in this module 2511 # eg. Files = (gid_a_b_c,gid_d_e_f) 2512 my $module_gids = $onemodule->{$itemname}; 2513 2514 # prune outer brackets 2515 $module_gids =~ s|^\s*\(||g; 2516 $module_gids =~ s|\)\s*$||g; 2517 for my $id (split (/,/, $module_gids)) 2518 { 2519 chomp $id; 2520 insert_for_item(\%module_lookup_table, lc ($id), $onemodule->{'gid'}); 2521 } 2522 } 2523 2524 return \%module_lookup_table; 2525} 2526 2527######################################################################## 2528# Items like files do not know their modules 2529# This function is a helper of function "assigning_modules_to_items" 2530######################################################################## 2531 2532sub get_string_of_modulegids_for_itemgid 2533{ 2534 my ($module_lookup_table, $modulesref, $itemgid, $itemname) = @_; 2535 2536 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::get_string_of_modulegids_for_itemgid : $#{$modulesref} : $itemgid : $itemname"); } 2537 2538 my $allmodules = ""; 2539 my $haslanguagemodule = 0; 2540 my %foundmodules = (); 2541 2542 # print STDERR "lookup '" . lc($itemgid) . "'\n"; 2543 my $gid_list = $module_lookup_table->{lc($itemgid)}; 2544 2545 for my $gid (@{$gid_list}) 2546 { 2547 $foundmodules{$gid} = 1; 2548 $allmodules = $allmodules . "," . $gid; 2549 # Is this module a language module? This info should be stored at the file. 2550 if ( exists($installer::globals::alllangmodules{$gid}) ) { $haslanguagemodule = 1; } 2551 } 2552 2553 $allmodules =~ s/^\s*\,//; # removing leading comma 2554 2555 # Check: All modules or no module must have flag LANGUAGEMODULE 2556 if ( $haslanguagemodule ) 2557 { 2558 my $isreallylanguagemodule = installer::worker::key_in_a_is_also_key_in_b(\%foundmodules, \%installer::globals::alllangmodules); 2559 if ( ! $isreallylanguagemodule ) { installer::exiter::exit_program("ERROR: \"$itemgid\" is assigned to modules with flag \"LANGUAGEMODULE\" and also to modules without this flag! Modules: $allmodules", "get_string_of_modulegids_for_itemgid"); } 2560 } 2561 2562 # print STDERR "get_string_for_itemgid ($itemgid, $itemname) => $allmodules, $haslanguagemodule\n"; 2563 2564 return ($allmodules, $haslanguagemodule); 2565} 2566 2567######################################################## 2568# Items like files do not know their modules 2569# This function add the {'modules'} to these items 2570######################################################## 2571 2572sub assigning_modules_to_items 2573{ 2574 my ($modulesref, $itemsref, $itemname) = @_; 2575 2576 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::assigning_modules_to_items : $#{$modulesref} : $#{$itemsref} : $itemname"); } 2577 2578 my $infoline = ""; 2579 my $languageassignmenterror = 0; 2580 my @languageassignmenterrors = (); 2581 2582 my $module_lookup_table = build_modulegids_table($modulesref, $itemname); 2583 2584 for my $oneitem (@{$itemsref}) 2585 { 2586 my $itemgid = $oneitem->{'gid'}; 2587 2588 my $styles = ""; 2589 if ( $oneitem->{'Styles'} ) { $styles = $oneitem->{'Styles'}; } 2590 if (( $itemname eq "Dirs" ) && ( ! ( $styles =~ /\bCREATE\b/ ))) { next; } 2591 2592 if ( $itemgid eq "" ) 2593 { 2594 installer::exiter::exit_program("ERROR in item collection: No gid for item $oneitem->{'Name'}", "assigning_modules_to_items"); 2595 } 2596 2597 # every item can belong to many modules 2598 2599 my ($modulegids, $haslanguagemodule) = get_string_of_modulegids_for_itemgid($module_lookup_table, $modulesref, $itemgid, $itemname); 2600 2601 if ($modulegids eq "") 2602 { 2603 installer::exiter::exit_program("ERROR in file collection: No module found for $itemname $itemgid", "assigning_modules_to_items"); 2604 } 2605 2606 $oneitem->{'modules'} = $modulegids; 2607 $oneitem->{'haslanguagemodule'} = $haslanguagemodule; 2608 2609 # Important check: "ismultilingual" and "haslanguagemodule" must have the same value ! 2610 if (( $oneitem->{'ismultilingual'} ) && ( ! $oneitem->{'haslanguagemodule'} )) 2611 { 2612 $infoline = "Error: \"$oneitem->{'gid'}\" is multi lingual, but not in language pack (Assigned module: $modulegids)!\n"; 2613 push( @installer::globals::globallogfileinfo, $infoline); 2614 push( @languageassignmenterrors, $infoline ); 2615 $languageassignmenterror = 1; 2616 } 2617 if (( $oneitem->{'haslanguagemodule'} ) && ( ! $oneitem->{'ismultilingual'} )) 2618 { 2619 $infoline = "Error: \"$oneitem->{'gid'}\" is in language pack, but not multi lingual (Assigned module: $modulegids)!\n"; 2620 push( @installer::globals::globallogfileinfo, $infoline); 2621 push( @languageassignmenterrors, $infoline ); 2622 $languageassignmenterror = 1; 2623 } 2624 } 2625 2626 if ($languageassignmenterror) 2627 { 2628 for ( my $i = 0; $i <= $#languageassignmenterrors; $i++ ) { print "$languageassignmenterrors[$i]"; } 2629 installer::exiter::exit_program("ERROR: Incorrect assignments for language packs.", "assigning_modules_to_items"); 2630 } 2631 2632} 2633 2634################################################################################################# 2635# Root path (for instance /opt/openofficeorg20) needs to be added to directories, files and links 2636################################################################################################# 2637 2638sub add_rootpath_to_directories 2639{ 2640 my ($dirsref, $rootpath) = @_; 2641 2642 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::add_rootpath_to_directories : $#{$dirsref} : $rootpath"); } 2643 2644 for ( my $i = 0; $i <= $#{$dirsref}; $i++ ) 2645 { 2646 my $onedir = ${$dirsref}[$i]; 2647 my $dir = ""; 2648 2649 if ( $onedir->{'Dir'} ) { $dir = $onedir->{'Dir'}; } 2650 2651 if (!($dir =~ /\bPREDEFINED_/ )) 2652 { 2653 my $hostname = $onedir->{'HostName'}; 2654 $hostname = $rootpath . $installer::globals::separator . $hostname; 2655 $onedir->{'HostName'} = $hostname; 2656 } 2657 2658 # added 2659 2660 if ( $dir =~ /\bPREDEFINED_PROGDIR\b/ ) 2661 { 2662 my $hostname = $onedir->{'HostName'}; 2663 if ( $hostname eq "" ) { $onedir->{'HostName'} = $rootpath; } 2664 else { $onedir->{'HostName'} = $rootpath . $installer::globals::separator . $hostname; } 2665 } 2666 } 2667} 2668 2669sub add_rootpath_to_files 2670{ 2671 my ($filesref, $rootpath) = @_; 2672 2673 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::add_rootpath_to_files : $#{$filesref} : $rootpath"); } 2674 2675 for ( my $i = 0; $i <= $#{$filesref}; $i++ ) 2676 { 2677 my $onefile = ${$filesref}[$i]; 2678 my $destination = $onefile->{'destination'}; 2679 $destination = $rootpath . $installer::globals::separator . $destination; 2680 $onefile->{'destination'} = $destination; 2681 } 2682} 2683 2684sub add_rootpath_to_links 2685{ 2686 my ($linksref, $rootpath) = @_; 2687 2688 if ( $installer::globals::debug ) { installer::logger::debuginfo("installer::scriptitems::add_rootpath_to_links : $#{$linksref} : $rootpath"); } 2689 2690 for ( my $i = 0; $i <= $#{$linksref}; $i++ ) 2691 { 2692 my $onelink = ${$linksref}[$i]; 2693 my $styles = $onelink->{'Styles'}; 2694 2695 my $destination = $onelink->{'destination'}; 2696 $destination = $rootpath . $installer::globals::separator . $destination; 2697 $onelink->{'destination'} = $destination; 2698 2699 if (!($styles =~ /\bRELATIVE\b/ )) # for absolute links 2700 { 2701 my $destinationfile = $onelink->{'destinationfile'}; 2702 $destinationfile = $rootpath . $installer::globals::separator . $destinationfile; 2703 $onelink->{'destinationfile'} = $destinationfile; 2704 } 2705 } 2706} 2707 2708################################################################################# 2709# Collecting all parent gids 2710################################################################################# 2711 2712sub collect_all_parent_feature 2713{ 2714 my ($modulesref) = @_; 2715 2716 my @allparents = (); 2717 2718 my $found_root_module = 0; 2719 2720 for ( my $i = 0; $i <= $#{$modulesref}; $i++ ) 2721 { 2722 my $onefeature = ${$modulesref}[$i]; 2723 2724 my $parentgid = ""; 2725 if ( $onefeature->{'ParentID'} ) 2726 { 2727 $parentgid = $onefeature->{'ParentID'}; 2728 } 2729 2730 if ( $parentgid ne "" ) 2731 { 2732 if (! installer::existence::exists_in_array($parentgid, \@allparents)) 2733 { 2734 push(@allparents, $parentgid); 2735 } 2736 } 2737 2738 # Setting the global root module 2739 2740 if ( $parentgid eq "" ) 2741 { 2742 if ( $found_root_module ) { installer::exiter::exit_program("ERROR: Only one module without ParentID or with empty ParentID allowed ($installer::globals::rootmodulegid, $onefeature->{'gid'}).", "collect_all_parent_feature"); } 2743 $installer::globals::rootmodulegid = $onefeature->{'gid'}; 2744 $found_root_module = 1; 2745 $infoline = "Setting Root Module: $installer::globals::rootmodulegid\n"; 2746 push( @installer::globals::globallogfileinfo, $infoline); 2747 } 2748 2749 if ( ! $found_root_module ) { installer::exiter::exit_program("ERROR: Could not define root module. No module without ParentID or with empty ParentID exists.", "collect_all_parent_feature"); } 2750 2751 } 2752 2753 return \@allparents; 2754} 2755 2756################################################################################# 2757# Checking for every feature, whether it has children 2758################################################################################# 2759 2760sub set_children_flag 2761{ 2762 my ($modulesref) = @_; 2763 2764 my $allparents = collect_all_parent_feature($modulesref); 2765 2766 for ( my $i = 0; $i <= $#{$modulesref}; $i++ ) 2767 { 2768 my $onefeature = ${$modulesref}[$i]; 2769 my $gid = $onefeature->{'gid'}; 2770 2771 # is this gid a parent? 2772 2773 if ( installer::existence::exists_in_array($gid, $allparents) ) 2774 { 2775 $onefeature->{'has_children'} = 1; 2776 } 2777 else 2778 { 2779 $onefeature->{'has_children'} = 0; 2780 } 2781 } 2782} 2783 2784################################################################################# 2785# All modules, that use a template module, do now get the assignments of 2786# the template module. 2787################################################################################# 2788 2789sub resolve_assigned_modules 2790{ 2791 my ($modulesref) = @_; 2792 2793 # collecting all template modules 2794 2795 my %directaccess = (); 2796 2797 for ( my $i = 0; $i <= $#{$modulesref}; $i++ ) 2798 { 2799 my $onefeature = ${$modulesref}[$i]; 2800 my $styles = ""; 2801 if ( $onefeature->{'Styles'} ) { $styles = $onefeature->{'Styles'}; } 2802 if ( $styles =~ /\bTEMPLATEMODULE\b/ ) { $directaccess{$onefeature->{'gid'}} = $onefeature; } 2803 2804 # also looking for module with flag ROOT_BRAND_PACKAGE, to save is for further usage 2805 if ( $styles =~ /\bROOT_BRAND_PACKAGE\b/ ) 2806 { 2807 $installer::globals::rootbrandpackage = $onefeature->{'gid'}; 2808 $installer::globals::rootbrandpackageset = 1; 2809 } 2810 } 2811 2812 # looking, where template modules are assigned 2813 2814 for ( my $i = 0; $i <= $#{$modulesref}; $i++ ) 2815 { 2816 my $onefeature = ${$modulesref}[$i]; 2817 if ( $onefeature->{'Assigns'} ) 2818 { 2819 my $templategid = $onefeature->{'Assigns'}; 2820 2821 if ( ! exists($directaccess{$templategid}) ) 2822 { 2823 installer::exiter::exit_program("ERROR: Did not find definition of assigned template module \"$templategid\"", "resolve_assigned_modules"); 2824 } 2825 2826 # Currently no merging of Files, Dirs, ... 2827 # This has to be included here, if it is required 2828 my $item; 2829 foreach $item (@installer::globals::items_at_modules) 2830 { 2831 if ( exists($directaccess{$templategid}->{$item}) ) { $onefeature->{$item} = $directaccess{$templategid}->{$item}; } 2832 } 2833 } 2834 } 2835} 2836 2837################################################################################# 2838# Removing the template modules from the list, after all 2839# assignments are transferred to the "real" modules. 2840################################################################################# 2841 2842sub remove_template_modules 2843{ 2844 my ($modulesref) = @_; 2845 2846 my @modules = (); 2847 2848 for ( my $i = 0; $i <= $#{$modulesref}; $i++ ) 2849 { 2850 my $onefeature = ${$modulesref}[$i]; 2851 my $styles = ""; 2852 if ( $onefeature->{'Styles'} ) { $styles = $onefeature->{'Styles'}; } 2853 if ( $styles =~ /\bTEMPLATEMODULE\b/ ) { next; } 2854 2855 push(@modules, $onefeature); 2856 } 2857 2858 return \@modules; 2859} 2860 2861################################################################################# 2862# Collecting all modules with flag LANGUAGEMODULE in a global 2863# collector. 2864################################################################################# 2865 2866sub collect_all_languagemodules 2867{ 2868 my ($modulesref) = @_; 2869 2870 for ( my $i = 0; $i <= $#{$modulesref}; $i++ ) 2871 { 2872 my $onefeature = ${$modulesref}[$i]; 2873 my $styles = ""; 2874 if ( $onefeature->{'Styles'} ) { $styles = $onefeature->{'Styles'}; } 2875 if ( $styles =~ /\bLANGUAGEMODULE\b/ ) 2876 { 2877 if ( ! exists($onefeature->{'Language'}) ) { installer::exiter::exit_program("ERROR: \"$onefeature->{'gid'}\" has flag LANGUAGEMODULE, but does not know its language!", "collect_all_languagemodules"); } 2878 $installer::globals::alllangmodules{$onefeature->{'gid'}} = $onefeature->{'Language'}; 2879 # Collecting also the english names, that are used for nsis unpack directory for language packs 2880 my $lang = $onefeature->{'Language'}; 2881 my $name = ""; 2882 foreach my $localkey ( keys %{$onefeature} ) 2883 { 2884 if ( $localkey =~ /^\s*Name\s*\(\s*en-US\s*\)\s*$/ ) 2885 { 2886 $installer::globals::all_english_languagestrings{$lang} = $onefeature->{$localkey}; 2887 } 2888 } 2889 } 2890 } 2891} 2892 2893################################################################################# 2894# Selecting from all collected english language strings those, that are really 2895# required in this installation set. 2896################################################################################# 2897 2898sub select_required_language_strings 2899{ 2900 my ($modulesref) = @_; 2901 2902 for ( my $i = 0; $i <= $#{$modulesref}; $i++ ) 2903 { 2904 my $onefeature = ${$modulesref}[$i]; 2905 my $styles = ""; 2906 if ( $onefeature->{'Styles'} ) { $styles = $onefeature->{'Styles'}; } 2907 if ( $styles =~ /\bLANGUAGEMODULE\b/ ) 2908 { 2909 if ( ! exists($onefeature->{'Language'}) ) { installer::exiter::exit_program("ERROR: \"$onefeature->{'gid'}\" has flag LANGUAGEMODULE, but does not know its language!", "select_required_language_strings"); } 2910 my $lang = $onefeature->{'Language'}; 2911 2912 if (( exists($installer::globals::all_english_languagestrings{$lang}) ) && ( ! exists($installer::globals::all_required_english_languagestrings{$lang}) )) 2913 { 2914 $installer::globals::all_required_english_languagestrings{$lang} = $installer::globals::all_english_languagestrings{$lang}; 2915 } 2916 } 2917 } 2918} 2919 2920##################################################################################### 2921# Unixlinks are not always required. For Linux RPMs and Solaris Packages they are 2922# created dynamically. Exception: For package formats "installed" or "archive". 2923# In scp2 this unixlinks have the flag LAYERLINK. 2924##################################################################################### 2925 2926sub filter_layerlinks_from_unixlinks 2927{ 2928 my ( $unixlinksref ) = @_; 2929 2930 my @alllinks = (); 2931 2932 for ( my $i = 0; $i <= $#{$unixlinksref}; $i++ ) 2933 { 2934 my $isrequired = 1; 2935 2936 my $onelink = ${$unixlinksref}[$i]; 2937 my $styles = ""; 2938 if ( $onelink->{'Styles'} ) { $styles = $onelink->{'Styles'}; } 2939 2940 if ( $styles =~ /\bLAYERLINK\b/ ) 2941 { 2942 # Platforms, that do not need the layer links 2943 if (( $installer::globals::islinuxrpmbuild ) || ( $installer::globals::issolarispkgbuild )) 2944 { 2945 $isrequired = 0; 2946 } 2947 2948 # Package formats, that need the layer link (platform independent) 2949 if (( $installer::globals::packageformat eq "installed" ) || ( $installer::globals::packageformat eq "archive" )) 2950 { 2951 $isrequired = 1; 2952 } 2953 } 2954 2955 if ( $isrequired ) { push(@alllinks, $onelink); } 2956 } 2957 2958 return \@alllinks; 2959} 2960 29611; 2962