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 24 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_rsc.hxx" 26 27 #include <stdlib.h> 28 #include <stdio.h> 29 #include <fcntl.h> 30 #include <string.h> 31 #if defined (WNT) && defined (tcpp) 32 #define _spawnvp spawnvp 33 #define _P_WAIT P_WAIT 34 #endif 35 36 #ifdef UNX 37 #include <unistd.h> 38 #include <sys/wait.h> 39 #else // UNX 40 41 #include <io.h> 42 #include <process.h> 43 #if defined ( OS2 ) && !defined ( GCC ) 44 #include <direct.h> 45 #endif 46 #if !defined ( CSET ) && !defined ( OS2 ) 47 #include <dos.h> 48 #endif 49 50 #endif // UNX 51 #include <rsctools.hxx> 52 #include <rscerror.h> 53 #include <sal/main.h> 54 #include <tools/fsys.hxx> 55 56 /*************** C O D E ************************************************/ 57 /****************************************************************/ 58 /* */ 59 /* Function : fuer Ansi kompatibilitaet */ 60 /* */ 61 /****************************************************************/ 62 #ifdef UNX 63 #define P_WAIT 0 64 int spawnvp( int, const char * cmdname, char *const* argv ){ 65 int rc(0); 66 67 switch( fork() ){ 68 case -1: 69 return( -1 ); 70 case 0: 71 if( execvp( cmdname, argv ) == -1 ) 72 // an error occurs 73 return( -1 ); 74 break; 75 default: 76 if( -1 == wait( &rc ) ) 77 return( -1 ); 78 } 79 return( WEXITSTATUS( rc ) ); 80 } 81 #endif 82 83 /************************************************************************* 84 |* CallPrePro() 85 |* 86 |* Beschreibung 87 *************************************************************************/ 88 static sal_Bool CallPrePro( const ByteString& rPrePro, 89 const ByteString& rInput, 90 const ByteString& rOutput, 91 RscPtrPtr * pCmdLine, 92 sal_Bool bResponse ) 93 { 94 RscPtrPtr aNewCmdL; // Kommandozeile 95 RscPtrPtr aRespCmdL; // Kommandozeile 96 RscPtrPtr * pCmdL = &aNewCmdL; 97 int i, nExit; 98 FILE* fRspFile = NULL; 99 ByteString aRspFileName; 100 101 if( bResponse ) 102 { 103 aRspFileName = ::GetTmpFileName(); 104 fRspFile = fopen( aRspFileName.GetBuffer(), "w" ); 105 } 106 107 if( !fRspFile ) 108 aNewCmdL.Append( rsc_strdup( rPrePro.GetBuffer() ) ); 109 110 bool bVerbose = false; 111 for( i = 1; i < int(pCmdLine->GetCount() -1); i++ ) 112 { 113 if ( 0 == rsc_stricmp( (char *)pCmdLine->GetEntry( i ), "-verbose" ) ) 114 { 115 bVerbose = true; 116 continue; 117 } 118 if ( !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-u", 2 ) 119 || !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-i", 2 ) 120 || !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-d", 2 ) 121 ) 122 { 123 aNewCmdL.Append( rsc_strdup( (char *)pCmdLine->GetEntry( i ) ) ); 124 } 125 } 126 127 aNewCmdL.Append( rsc_strdup( rInput.GetBuffer() ) ); 128 aNewCmdL.Append( rsc_strdup( rOutput.GetBuffer() ) ); 129 aNewCmdL.Append( (void *)0 ); 130 131 if ( bVerbose ) 132 { 133 printf( "Preprocessor commandline: " ); 134 for( i = 0; i < (int)(pCmdL->GetCount() -1); i++ ) 135 { 136 printf( " " ); 137 printf( "%s", (const char *)pCmdL->GetEntry( i ) ); 138 } 139 printf( "\n" ); 140 } 141 142 if( fRspFile ) 143 { 144 aRespCmdL.Append( rsc_strdup( rPrePro.GetBuffer() ) ); 145 ByteString aTmpStr( '@' ); 146 aTmpStr += aRspFileName; 147 aRespCmdL.Append( rsc_strdup( aTmpStr.GetBuffer() ) ); 148 aRespCmdL.Append( (void *)0 ); 149 150 pCmdL = &aRespCmdL; 151 for( i = 0; i < (int)(aNewCmdL.GetCount() -1); i++ ) 152 { 153 #ifdef OS2 154 fprintf( fRspFile, "%s\n", (const char *)aNewCmdL.GetEntry( i ) ); 155 #else 156 fprintf( fRspFile, "%s ", (const char *)aNewCmdL.GetEntry( i ) ); 157 #endif 158 } 159 fclose( fRspFile ); 160 161 if ( bVerbose ) 162 { 163 printf( "Preprocessor startline: " ); 164 for( i = 0; i < (int)(pCmdL->GetCount() -1); i++ ) 165 { 166 printf( " " ); 167 printf( "%s", (const char *)pCmdL->GetEntry( i ) ); 168 } 169 printf( "\n" ); 170 } 171 } 172 173 #if ((defined OS2 || defined WNT) && (defined TCPP || defined tcpp)) || defined UNX || defined OS2 174 nExit = spawnvp( P_WAIT, rPrePro.GetBuffer(), (char* const*)pCmdL->GetBlock() ); 175 #elif defined CSET 176 nExit = spawnvp( P_WAIT, (char*)rPrePro.GetBuffer(), (const char**)pCmdL->GetBlock() ); 177 #elif defined WTC 178 nExit = spawnvp( P_WAIT, (char*)rPrePro.GetBuffer(), (const char* const*)pCmdL->GetBlock() ); 179 #elif defined MTW 180 nExit = spawnvp( P_WAIT, (char*)rPrePro.GetBuffer(), (char**)pCmdL->GetBlock() ); 181 #else 182 nExit = spawnvp( P_WAIT, (char*)rPrePro.GetBuffer(), (const char**)pCmdL->GetBlock() ); 183 #endif 184 185 if ( fRspFile ) 186 #if OSL_DEBUG_LEVEL > 5 187 fprintf( stderr, "leaving response file %s\n", aRspFileName.GetBuffer() ); 188 #else 189 unlink( aRspFileName.GetBuffer() ); 190 #endif 191 if ( nExit ) 192 return sal_False; 193 194 return sal_True; 195 } 196 197 198 /************************************************************************* 199 |* CallRsc2 200 |* 201 |* Beschreibung 202 *************************************************************************/ 203 static sal_Bool CallRsc2( ByteString aRsc2Name, 204 RscStrList * pInputList, 205 ByteString aSrsName, 206 RscPtrPtr * pCmdLine ) 207 { 208 int i, nExit; 209 ByteString* pString; 210 ByteString aRspFileName; // Response-Datei 211 FILE * fRspFile; // Response-Datei 212 213 aRspFileName = ::GetTmpFileName(); 214 fRspFile = fopen( aRspFileName.GetBuffer(), "w" ); 215 216 RscVerbosity eVerbosity = RscVerbosityNormal; 217 if( fRspFile ) 218 { 219 for( i = 1; i < (int)(pCmdLine->GetCount() -1); i++ ) 220 { 221 if ( !rsc_stricmp( (char *)pCmdLine->GetEntry( i ), "-verbose" ) ) 222 { 223 eVerbosity = RscVerbosityVerbose; 224 continue; 225 } 226 if ( !rsc_stricmp( (char *)pCmdLine->GetEntry( i ), "-quiet" ) ) 227 { 228 eVerbosity = RscVerbositySilent; 229 continue; 230 } 231 if( !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-fp=", 4 ) 232 || !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-fo=", 4 ) 233 || !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-pp=", 4 ) 234 || !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-rsc2=", 6 ) 235 || !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-presponse", 9 ) 236 || !rsc_strnicmp( (char *)pCmdLine->GetEntry( i ), "-rc", 3 ) 237 || !rsc_stricmp( (char *)pCmdLine->GetEntry( i ), "-+" ) 238 || !rsc_stricmp( (char *)pCmdLine->GetEntry( i ), "-br" ) 239 || !rsc_stricmp( (char *)pCmdLine->GetEntry( i ), "-bz" ) 240 || !rsc_stricmp( (char *)pCmdLine->GetEntry( i ), "-r" ) 241 // Am I the only one that thinks the following line inludes all the tests before? 242 || ( '-' != *(char *)pCmdLine->GetEntry( i ) ) ) 243 { 244 } 245 else 246 #ifdef OS2 247 fprintf( fRspFile, "%s\n", 248 #else 249 fprintf( fRspFile, "%s ", 250 #endif 251 (const char *)pCmdLine->GetEntry( i ) ); 252 }; 253 254 #ifdef OS2 255 fprintf( fRspFile, "%s\n", aSrsName.GetBuffer() ); 256 #else 257 fprintf( fRspFile, aSrsName.GetBuffer() ); 258 #endif 259 260 pString = pInputList->First(); 261 while( pString ) 262 { 263 #ifdef OS2 264 fprintf( fRspFile, "%s\n", pString->GetBuffer() ); 265 #else 266 fprintf( fRspFile, " %s", pString->GetBuffer() ); 267 #endif 268 pString = pInputList->Next(); 269 }; 270 271 fclose( fRspFile ); 272 }; 273 274 RscPtrPtr aNewCmdL; // Kommandozeile 275 aNewCmdL.Append( rsc_strdup( aRsc2Name.GetBuffer() ) ); 276 ByteString aTmpStr( '@' ); 277 aTmpStr += aRspFileName; 278 aNewCmdL.Append( rsc_strdup( aTmpStr.GetBuffer() ) ); 279 aNewCmdL.Append( (void *)0 ); 280 281 if ( eVerbosity >= RscVerbosityVerbose ) 282 { 283 printf( "Rsc2 commandline: " ); 284 printf( "%s", (const char *)aNewCmdL.GetEntry( 0 ) ); 285 printf( " " ); 286 printf( "%s", (const char *)aNewCmdL.GetEntry( 1 ) ); 287 printf( "\n" ); 288 } 289 290 #if ((defined OS2 || defined WNT) && (defined TCPP || defined tcpp)) || defined UNX || defined OS2 291 nExit = spawnvp( P_WAIT, aRsc2Name.GetBuffer(), (char* const*)aNewCmdL.GetBlock() ); 292 #elif defined CSET 293 nExit = spawnvp( P_WAIT, (char*)aRsc2Name.GetBuffer(), (char **)(const char**)aNewCmdL.GetBlock() ); 294 #elif defined WTC 295 nExit = spawnvp( P_WAIT, (char*)aRsc2Name.GetBuffer(), (const char* const*)aNewCmdL.GetBlock() ); 296 #elif defined MTW 297 nExit = spawnvp( P_WAIT, (char*)aRsc2Name.GetBuffer(), (char**)aNewCmdL.GetBlock() ); 298 #else 299 nExit = spawnvp( P_WAIT, (char*)aRsc2Name.GetBuffer(), (const char**)aNewCmdL.GetBlock() ); 300 #endif 301 302 if( fRspFile ) 303 #if OSL_DEBUG_LEVEL > 5 304 fprintf( stderr, "leaving response file %s\n", aRspFileName.GetBuffer() ); 305 #else 306 unlink( aRspFileName.GetBuffer() ); 307 #endif 308 if( nExit ) 309 return( sal_False ); 310 return( sal_True ); 311 } 312 313 /************************************************************************* 314 |* 315 |* main() 316 |* 317 |* Beschreibung 318 |* Ersterstellung MM 05.09.91 319 |* Letzte Aenderung MM 05.09.91 320 |* 321 *************************************************************************/ 322 SAL_IMPLEMENT_MAIN_WITH_ARGS(argc, argv) 323 { 324 sal_Bool bPrePro = sal_True; 325 sal_Bool bResFile = sal_True; 326 sal_Bool bHelp = sal_False; 327 sal_Bool bError = sal_False; 328 sal_Bool bResponse = sal_False; 329 ByteString aSolarbin(getenv("SOLARBINDIR")); 330 ByteString aDelim("/"); 331 ByteString aPrePro; //( aSolarbin + aDelim + ByteString("rscpp")); 332 ByteString aRsc2Name; //( aSolarbin + aDelim + ByteString("rsc2")); 333 ByteString aSrsName; 334 ByteString aResName; 335 RscStrList aInputList; 336 RscStrList aTmpList; 337 char * pStr; 338 char ** ppStr; 339 RscPtrPtr aCmdLine; // Kommandozeile 340 sal_uInt32 i; 341 ByteString* pString; 342 343 aPrePro = aSolarbin; 344 aPrePro += aDelim; 345 aPrePro += ByteString("rscpp"); 346 347 aRsc2Name = aSolarbin; 348 aRsc2Name += aDelim; 349 aRsc2Name += ByteString("rsc2"); 350 351 pStr = ::ResponseFile( &aCmdLine, argv, argc ); 352 if( pStr ) 353 { 354 printf( "Cannot open response file <%s>\n", pStr ); 355 return( 1 ); 356 }; 357 358 ppStr = (char **)aCmdLine.GetBlock(); 359 ppStr++; 360 i = 1; 361 sal_Bool bSetSrs = sal_False; 362 while( ppStr && i < (aCmdLine.GetCount() -1) ) 363 { 364 if( '-' == **ppStr ) 365 { 366 if( !rsc_stricmp( (*ppStr) + 1, "p" ) 367 || !rsc_stricmp( (*ppStr) + 1, "l" ) ) 368 { // kein Preprozessor 369 bPrePro = sal_False; 370 } 371 else if( !rsc_stricmp( (*ppStr) + 1, "r" ) 372 || !rsc_stricmp( (*ppStr) + 1, "s" ) ) 373 { // erzeugt kein .res-file 374 bResFile = sal_False; 375 } 376 else if( !rsc_stricmp( (*ppStr) + 1, "h" ) ) 377 { // Hilfe anzeigen 378 bHelp = sal_True; 379 } 380 else if( !rsc_strnicmp( (*ppStr) + 1, "presponse", 9 ) ) 381 { // anderer Name fuer den Preprozessor 382 bResponse = sal_True; 383 } 384 else if( !rsc_strnicmp( (*ppStr) + 1, "pp=", 3 ) ) 385 { // anderer Name fuer den Preprozessor 386 aPrePro = (*ppStr) + 4; 387 } 388 else if( !rsc_strnicmp( (*ppStr) + 1, "rsc2=", 5 ) ) 389 { // Accept alternate name for the rsc2 compiler 390 aRsc2Name = (*ppStr) + 6; 391 } 392 else if( !rsc_strnicmp( (*ppStr) + 1, "fo=", 3 ) ) 393 { // anderer Name fuer .res-file 394 aResName = (*ppStr) + 4; 395 } 396 else if( !rsc_strnicmp( (*ppStr) + 1, "fp=", 3 ) ) 397 { // anderer Name fuer .srs-file 398 bSetSrs = sal_True; 399 aSrsName = (*ppStr); 400 } 401 } 402 else 403 { 404 // Eingabedatei 405 aInputList.Insert( new ByteString( *ppStr ), CONTAINER_APPEND ); 406 } 407 ppStr++; 408 i++; 409 } 410 411 if( aInputList.Count() ) 412 { 413 /* build the output file names */ 414 if( ! aResName.Len() ) 415 aResName = OutputFile( *aInputList.First(), "res" ); 416 if( ! bSetSrs ) 417 { 418 aSrsName = "-fp="; 419 aSrsName += OutputFile( *aInputList.First(), "srs" ); 420 } 421 }; 422 423 if( bHelp ) 424 { 425 bPrePro = sal_False; 426 bResFile = sal_False; 427 }; 428 if( bPrePro && aInputList.Count() ) 429 { 430 ByteString aTmpName; 431 432 pString = aInputList.First(); 433 while( pString ) 434 { 435 aTmpName = ::GetTmpFileName(); 436 if( !CallPrePro( aPrePro, *pString, aTmpName, &aCmdLine, bResponse ) ) 437 { 438 printf( "Error starting preprocessor\n" ); 439 bError = sal_True; 440 break; 441 } 442 aTmpList.Insert( new ByteString( aTmpName ), CONTAINER_APPEND ); 443 pString = aInputList.Next(); 444 }; 445 }; 446 447 if( !bError ) 448 { 449 if( !CallRsc2( aRsc2Name, bPrePro ? &aTmpList : &aInputList, 450 aSrsName, &aCmdLine ) ) 451 { 452 if( !bHelp ) 453 { 454 printf( "Error starting rsc2 compiler\n" ); 455 bError = sal_True; 456 } 457 }; 458 }; 459 460 pString = aTmpList.First(); 461 while( pString ) 462 { 463 #if OSL_DEBUG_LEVEL > 5 464 fprintf( stderr, "leaving temp file %s\n", pString->GetBuffer() ); 465 #else 466 unlink( pString->GetBuffer() ); 467 #endif 468 pString = aTmpList.Next(); 469 }; 470 471 return( bError ); 472 } 473 474 void RscExit( sal_uInt32 nExit ) 475 { 476 if( nExit ) 477 printf( "Program exit is %d\n", (int)nExit ); 478 exit( nExit ); 479 } 480