00001 #include <stdlib.h>
00002 #include <opie2/odebug.h>
00003 #include <qpe/qpeapplication.h>
00004 #include <qtextstream.h>
00005 #include <qdir.h>
00006 #include <qfile.h>
00007 #include <qfileinfo.h>
00008
00009 #include "nsdata.h"
00010 #include <netnode.h>
00011 #include <resources.h>
00012
00013 static QString CfgFile;
00014
00015 NetworkSettingsData::NetworkSettingsData( void ) {
00016
00017 new TheNSResources();
00018
00019 if( ! NSResources->userKnown() ) {
00020 Log(( "Cannot detect qpe user HOME=\"%s\" USER=\"%s\"\n",
00021 NSResources->currentUser().HomeDir.latin1(),
00022 NSResources->currentUser().UserName.latin1() ));
00023 return;
00024 }
00025
00026 CfgFile.sprintf( "%s/Settings/NS2.conf",
00027 NSResources->currentUser().HomeDir.latin1() );
00028 Log(( "Cfg from %s\n", CfgFile.latin1() ));
00029
00030
00031 loadSettings();
00032
00033
00034 { QDir D( "/tmp" );
00035 QFile * F = new QFile;
00036 int profilenr;
00037 QString interfacename;
00038 QTextStream TS ( F );
00039
00040 QStringList SL = D.entryList( "profile-*.up");
00041
00042 Log(( "System reports %d interfaces. Found %d up\n",
00043 NSResources->system().interfaces().count(),
00044 SL.count() ));
00045
00046 for ( QStringList::Iterator it = SL.begin();
00047 it != SL.end();
00048 ++it ) {
00049 profilenr = atol( (*it).mid( 8 ).latin1() );
00050
00051 F->setName( D.path() + "/" + (*it) );
00052 if( F->open( IO_ReadOnly ) ) {
00053 NetworkSetup * NC;
00054 interfacename = TS.readLine();
00055 F->close();
00056
00057 Log(( "Assign interface %s to Profile nr %d\n",
00058 interfacename.latin1(), profilenr ));
00059
00060 NC = NSResources->getNetworkSetup( profilenr );
00061 if( NC ) {
00062 NC->assignInterface(
00063 NSResources->system().findInterface( interfacename ) );
00064 Log(( "Assign interface %p\n",
00065 NC->assignedInterface() ));
00066 } else {
00067 Log(( "Profile nr %d no longer defined\n",
00068 profilenr ));
00069 }
00070 }
00071 }
00072 }
00073 }
00074
00075
00076 NetworkSettingsData::~NetworkSettingsData( void ) {
00077 delete NSResources;
00078 }
00079
00080 void NetworkSettingsData::loadSettings( void ) {
00081 QString Line, S;
00082 QString Attr, Value;
00083 long idx;
00084
00085 QFile F( CfgFile );
00086 QTextStream TS( &F );
00087
00088 ForceModified = 0;
00089
00090 do {
00091
00092 if( ! F.open(IO_ReadOnly) )
00093 break;
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106
00107 while( ! TS.atEnd() ) {
00108 S = Line = TS.readLine();
00109
00110 if ( S.isEmpty() || S[0] != '[' )
00111 continue;
00112
00113 S = S.mid( 1, S.length()-2 );
00114
00115 if( ! NSResources ) {
00116 continue;
00117 }
00118
00119 if( S == "NetworkSetup" ) {
00120
00121 bool Dangling;
00122 NetworkSetup * NC = new NetworkSetup( TS, Dangling );
00123 NSResources->addNetworkSetup( NC, Dangling );
00124 } else {
00125 ANetNode * NN = 0;
00126 ANetNodeInstance* NNI = 0;
00127 if( S.startsWith( "nodetype " ) ) {
00128 S = S.mid( 9, S.length()-9 );
00129 S = deQuote(S);
00130
00131 NN = NSResources->findNetNode( S );
00132 } else {
00133
00134 NNI = NSResources->createNodeInstance( S );
00135 }
00136
00137 if( NN == 0 && NNI == 0 ) {
00138 LeftOvers.append( Line );
00139 do {
00140 Line = TS.readLine();
00141
00142 LeftOvers.append( Line );
00143 } while ( ! Line.isEmpty() );
00144
00145
00146 continue;
00147 }
00148
00149
00150 do {
00151 S = Line = TS.readLine();
00152
00153 if( S.isEmpty() ) {
00154
00155 break;
00156 }
00157 idx = S.find( '=' );
00158 if( idx > 0 ) {
00159 Attr = S.left( idx );
00160 Value = S.mid( idx+1, S.length() );
00161 } else {
00162 Value="";
00163 Attr = S;
00164 }
00165
00166 Value.stripWhiteSpace();
00167 Attr.stripWhiteSpace();
00168 Attr.lower();
00169
00170 Value = deQuote(Value);
00171
00172 if( NN ) {
00173
00174 NN->setAttribute( Attr, Value );
00175 } else {
00176
00177 NNI->setAttribute( Attr, Value );
00178 }
00179 } while( 1 );
00180
00181 if( NNI ) {
00182
00183 Log( ( "NodeInstance %s : %p\n", NNI->name(), NNI ));
00184 NNI->setNew( FALSE );
00185 NSResources->addNodeInstance( NNI );
00186 }
00187
00188 if( NN ) {
00189 Log( ( "Node %s : %p\n", NN->name(), NN ) );
00190 }
00191 }
00192 }
00193
00194 } while( 0 );
00195
00196 }
00197
00198 QString NetworkSettingsData::saveSettings( void ) {
00199 QString ErrS = "";
00200
00201 if( ! isModified() )
00202 return ErrS;
00203
00204 QString S;
00205 QFile F( CfgFile + ".bup" );
00206
00207 Log( ( "Saving settings to %s\n", CfgFile.latin1() ));
00208 if( ! F.open( IO_WriteOnly | IO_Truncate ) ) {
00209 ErrS = qApp->translate( "NetworkSettings",
00210 "<p>Could not save setup to \"%1\" !</p>" ).
00211 arg(CfgFile);
00212
00213 return ErrS;
00214 }
00215
00216 QTextStream TS( &F );
00217
00218
00219 for( QDictIterator<ANetNode> it( NSResources->netNodes() );
00220 it.current();
00221 ++it ) {
00222 TS << "[nodetype "
00223 << quote( QString( it.current()->name() ) )
00224 << "]"
00225 << endl;
00226
00227 it.current()->saveAttributes( TS );
00228 TS << endl;
00229 }
00230
00231
00232 for ( QStringList::Iterator it = LeftOvers.begin();
00233 it != LeftOvers.end(); ++it ) {
00234 TS << (*it) << endl;
00235 }
00236
00237
00238 { ANetNodeInstance * NNI;
00239 for( QDictIterator<ANetNodeInstance> nit(
00240 NSResources->netNodeInstances());
00241 nit.current();
00242 ++nit ) {
00243
00244 NNI = nit.current();
00245 TS << '['
00246 << QString(NNI->nodeClass()->name())
00247 << ']'
00248 << endl;
00249 NNI->saveAttributes( TS );
00250 TS << endl;
00251 }
00252 }
00253
00254
00255 { Name2NetworkSetup_t & M = NSResources->networkSetups();
00256
00257
00258 for( QDictIterator<NetworkSetup> it(M);
00259 it.current();
00260 ++it ) {
00261 TS << "[NetworkSetup]" << endl;
00262 it.current()->save(TS);
00263 }
00264 }
00265
00266
00267 { Name2NetworkSetup_t & M = NSResources->danglingNetworkSetups();
00268
00269
00270 for( QDictIterator<NetworkSetup> it(M);
00271 it.current();
00272 ++it ) {
00273 TS << "[NetworkSetup]" << endl;
00274 it.current()->save(TS);
00275 }
00276 }
00277
00278 QDir D(".");
00279 D.rename( CfgFile + ".bup", CfgFile );
00280
00281
00282
00283
00284
00285
00286 for( QDictIterator<NetworkSetup> it(NSResources->networkSetups());
00287 it.current();
00288 ++it ) {
00289 it.current()->setModified( 0 );
00290 }
00291
00292 return ErrS;
00293 }
00294
00295 QString NetworkSettingsData::generateSettings( void ) {
00296 QString S = "";
00297 Name2SystemFile_t & SFM = NSResources->systemFiles();
00298 Name2NetworkSetup_t & M = NSResources->networkSetups();
00299 NetworkSetup * NC;
00300 ANetNodeInstance * NNI;
00301 ANetNodeInstance * FirstWithData;
00302 RuntimeInfo * CurDev;
00303 ANetNode * NN, * CurDevNN = 0;
00304 long NoOfDevs;
00305 long DevCtStart;
00306 bool needToGenerate;
00307
00308
00309 Log( ( "Generating settings from %s\n", CfgFile.latin1() ));
00310
00311 for( QDictIterator<ANetNode> nnit( NSResources->netNodes() );
00312 nnit.current();
00313 ++nnit ) {
00314 bool FirstItem = 1;
00315 bool Generated = 0;
00316
00317 CurDevNN = nnit.current();
00318
00319 { QStringList SL;
00320 SL = CurDevNN->properFiles();
00321
00322 for ( QStringList::Iterator it = SL.begin();
00323 it != SL.end();
00324 ++it ) {
00325
00326 Generated = 0;
00327 FirstItem = 1;
00328
00329 for( QDictIterator<ANetNodeInstance> nniit(
00330 NSResources->netNodeInstances() );
00331 nniit.current();
00332 ++nniit ) {
00333 if( nniit.current()->nodeClass() != CurDevNN )
00334
00335 continue;
00336
00337
00338 { SystemFile SF( (*it) );
00339 QStringList SL;
00340
00341 if( ! CurDevNN->openFile( SF, nniit.current(), SL) ) {
00342
00343 S = qApp->translate( "NetworkSettings",
00344 "<p>Cannot build proper file \"%1\" for node \"%2\"</p>" ).
00345 arg( (*it) ).
00346 arg( CurDevNN->name() );
00347 return S;
00348 }
00349
00350 if( ! createPath( SL ) ) {
00351 S = qApp->translate( "NetworkSettings",
00352 "<p>Cannot create path \"%1\" for proper file \"%2\" for node \"%3\"</p>" ).
00353 arg( SL.join("/") ).
00354 arg( (*it) ).
00355 arg( CurDevNN->name() );
00356 return S;
00357 }
00358
00359 if( ! SF.open() ) {
00360 S = qApp->translate( "NetworkSettings",
00361 "<p>Cannot open proper file \"%1\" for node \"%2\"</p>" ).
00362 arg( (*it) ).arg( CurDevNN->name() );
00363 return S;
00364 }
00365
00366
00367 if( FirstItem ) {
00368 if( CurDevNN->generatePreamble( SF ) == 2 ) {
00369 S = qApp->translate( "NetworkSettings",
00370 "<p>Error in section \"preamble\" for proper file \"%1\" and node \"%2\"</p>" ).
00371 arg( (*it) ).
00372 arg( CurDevNN->name() );
00373 return S;
00374 }
00375 }
00376 FirstItem = 0;
00377 Generated = 1;
00378
00379
00380 if( nniit.current()->generateFile( SF, -1 ) == 2 ) {
00381 S = qApp->translate( "NetworkSettings",
00382 "<p>Error in section for node \"%1\" for proper file \"%2\" and node class \"%3\"</p>" ).
00383 arg( nniit.current()->name() ).
00384 arg( (*it) ).
00385 arg( CurDevNN->name() );
00386 return S;
00387 }
00388 }
00389 }
00390
00391 if( Generated ) {
00392 SystemFile SF( (*it) );
00393 QStringList SL;
00394
00395 if( CurDevNN->openFile( SF, 0, SL ) &&
00396 ! SF.path().isEmpty()
00397 ) {
00398
00399 if( ! createPath( SL ) ) {
00400 S = qApp->translate( "NetworkSettings",
00401 "<p>Cannot create path \"%1\" for proper file \"%2\" for node \"%3\"</p>" ).
00402 arg( SL.join("/") ).
00403 arg( (*it) ).
00404 arg( CurDevNN->name() );
00405 return S;
00406 }
00407
00408 if( ! SF.open() ) {
00409 S = qApp->translate( "NetworkSettings",
00410 "<p>Cannot open proper file \"%1\" for node \"%2\"</p>" ).
00411 arg( (*it) ).
00412 arg( CurDevNN->name() );
00413 return S;
00414 }
00415
00416 if( CurDevNN->generatePostamble( SF ) == 2 ) {
00417 S = qApp->translate( "NetworkSettings",
00418 "<p>Error in section \"postamble\" for proper file \"%1\" and node \"%2\"</p>" ).
00419 arg( (*it) ).
00420 arg( CurDevNN->name() );
00421 return S;
00422 }
00423 }
00424 }
00425 }
00426 }
00427 }
00428
00429
00430
00431
00432 for( QDictIterator<SystemFile> sfit(SFM);
00433 sfit.current();
00434 ++sfit ) {
00435 SystemFile * SF;
00436
00437 SF = sfit.current();
00438
00439
00440 for( QDictIterator<ANetNode> nnit( NSResources->netNodes() );
00441 nnit.current();
00442 ++nnit ) {
00443 nnit.current()->setDone(0);
00444 }
00445
00446 for( QDictIterator<ANetNodeInstance> nniit(
00447 NSResources->netNodeInstances() );
00448 nniit.current();
00449 ++nniit ) {
00450 nniit.current()->setDone(0);
00451 }
00452
00453 for( QDictIterator<NetworkSetup> ncit(M);
00454 ncit.current();
00455 ++ncit ) {
00456 ncit.current()->setDone(0);
00457 }
00458
00459 Log( ( "Generating system file %s\n", SF->name().latin1() ));
00460
00461 needToGenerate = 0;
00462
00463
00464
00465 for( QDictIterator<ANetNode> nnit( NSResources->netNodes() );
00466 ! needToGenerate && nnit.current();
00467 ++nnit ) {
00468
00469 NN = nnit.current();
00470
00471 if( NN->hasDataForFile( *SF ) ) {
00472
00473
00474
00475 for( QDictIterator<ANetNodeInstance> nniit(
00476 NSResources->netNodeInstances() );
00477 ! needToGenerate && nniit.current();
00478 ++nniit ) {
00479 if( nniit.current()->nodeClass() == NN ) {
00480
00481 Log(("Node %s has data\n",
00482 nniit.current()->name() ));
00483 needToGenerate = 1;
00484 break;
00485 }
00486 }
00487 }
00488 }
00489
00490 if( ! needToGenerate ) {
00491
00492
00493 Log(("No nodes for systemfile %s\n", SF->name().latin1() ));
00494 continue;
00495 }
00496
00497
00498 if( ! SF->open() ) {
00499 S = qApp->translate( "NetworkSettings",
00500 "<p>Cannot open system file \"%1\"</p>" ).
00501 arg( SF->name() );
00502 return S;
00503 }
00504
00505
00506 if( ! SF->preSection() ) {
00507 S = qApp->translate( "NetworkSettings",
00508 "<p>Error in section \"Preamble\" for file \"%1\"</p>" ).
00509 arg( SF->name() );
00510 return S;
00511 }
00512
00513
00514 for( QDictIterator<NetworkSetup> ncit(M);
00515 ncit.current();
00516 ++ncit ) {
00517
00518 NC = ncit.current();
00519
00520 if( NC->done() ) {
00521
00522 continue;
00523 }
00524
00525 if( ! NC->hasDataForFile( *SF ) ) {
00526
00527 continue;
00528 }
00529
00530 Log(("Generating %s for NetworkSetup %s\n",
00531 SF->name().latin1(), NC->name().latin1() ));
00532
00533 FirstWithData = NC->firstWithDataForFile( *SF );
00534
00535
00536 CurDev = NC->device();
00537
00538 CurDevNN = CurDev->netNode()->nodeClass();
00539
00540 if( ! FirstWithData->nodeClass()->done() ) {
00541
00542 if( ! SF->preDeviceSection( CurDevNN ) ) {
00543 S = qApp->translate( "NetworkSettings",
00544 "<p>Error in section \"Pre-Device\" for file \"%1\"</p>" ).
00545 arg( SF->name() );
00546 return S;
00547 }
00548
00549 if( FirstWithData->nodeClass()->generateFile(
00550 *SF,
00551 FirstWithData,
00552 -2 ) == 2 ) {
00553 S = qApp->translate( "NetworkSettings",
00554 "<p>Error in section \"Common\" for file \"%1\" and node \"%2\"</p>" ).
00555 arg( SF->name() ).
00556 arg( CurDevNN->name() );
00557 return S;
00558 }
00559 FirstWithData->nodeClass()->setDone( 1 );
00560 Log(( "Systemfile %s for node instance %s is done\n",
00561 SF->name().latin1(),
00562 FirstWithData->name() ));
00563 }
00564
00565 NoOfDevs = 0;
00566 DevCtStart = -1;
00567
00568 if( SF->knowsDeviceInstances() ) {
00569 DevCtStart = 0;
00570 NoOfDevs = CurDevNN->instanceCount();
00571 }
00572
00573 if( ! CurDev->netNode()->nodeClass()->done() ) {
00574
00575
00576 for( int i = DevCtStart; i < NoOfDevs ; i ++ ) {
00577
00578 if( FirstWithData->nodeClass()->generateFile(
00579 *SF, CurDev->netNode(), i ) == 2 ) {
00580 S = qApp->translate( "NetworkSettings",
00581 "<p>Error in section \"Device\" for file \"%1\" and node \"%2\"</p>" ).
00582 arg( SF->name() ).
00583 arg( CurDevNN->name() );
00584 return S;
00585 }
00586 }
00587 CurDev->netNode()->nodeClass()->setDone( 1 );
00588
00589 Log(( "Systemfile %s for Nodeclass %s is done\n",
00590 SF->name().latin1(),
00591 CurDev->netNode()->nodeClass()->name()
00592 ));
00593 }
00594
00595
00596
00597 for( QDictIterator<NetworkSetup> ncit2(M);
00598 ncit2.current();
00599 ++ncit2 ) {
00600
00601 if( ncit2.current()->device() != CurDev ) {
00602
00603 continue;
00604 }
00605
00606 Log(("NetworkSetup %s of family %s\n",
00607 ncit2.current()->name().latin1(),
00608 CurDev->name() ));
00609
00610 NNI = ncit2.current()->firstWithDataForFile( *SF );
00611 for( int i = DevCtStart; i < NoOfDevs ; i ++ ) {
00612 if( ! SF->preNodeSection( NNI, i ) ) {
00613 S = qApp->translate( "NetworkSettings",
00614 "<p>Error in \"Pre-Node Part\" for file \"%1\" and node \"%2\"</p>" ).
00615 arg( SF->name() ).
00616 arg( CurDevNN->name() );
00617 return S;
00618 }
00619
00620 switch( NNI->generateFile( *SF, i ) ) {
00621 case 0 :
00622 (*SF) << endl;
00623 break;
00624 case 1 :
00625 break;
00626 case 2 :
00627 S = qApp->translate( "NetworkSettings",
00628 "<p>Error in section \"Node\" for file \"%1\" and node \"%2\"</p>" ).
00629 arg( SF->name() ).
00630 arg( CurDevNN->name() );
00631 return S;
00632 }
00633
00634 if( ! SF->postNodeSection( NNI, i ) ) {
00635 S = qApp->translate( "NetworkSettings",
00636 "<p>Error in \"Post-Node Part\" for file \"%1\" and node \"%2\"</p>" ).
00637 arg( SF->name() ).
00638 arg( CurDevNN->name() );
00639 return S;
00640 }
00641 }
00642
00643 ncit2.current()->setDone( 1 );
00644
00645 }
00646 }
00647
00648 if( ! SF->postDeviceSection( CurDevNN ) ) {
00649 S = qApp->translate( "NetworkSettings",
00650 "<p>Error in section \"Post-Device\" for file \"%1\" and node \"%2\"</p>" ).
00651 arg( SF->name() ).
00652 arg( CurDevNN->name() );
00653 return S;
00654 }
00655
00656
00657 if( ! SF->postSection() ) {
00658 S = qApp->translate( "NetworkSettings",
00659 "<p>Error in section \"Closure\" for file \"%1\"</p>" ).
00660 arg( SF->name() );
00661 return S;
00662 }
00663
00664
00665 SF->close();
00666 }
00667 return S;
00668 }
00669
00670 QList<NetworkSetup> NetworkSettingsData::collectPossible(
00671 const QString & Interface ) {
00672
00673 NetworkSetup * NC;
00674 QList<NetworkSetup> PossibleNetworkSetups;
00675 Name2NetworkSetup_t & M = NSResources->networkSetups();
00676
00677
00678 for( QDictIterator<NetworkSetup> it(M);
00679 it.current();
00680 ++it ) {
00681 NC = it.current();
00682
00683 if( NC->handlesInterface( Interface ) &&
00684 NC->state() != Disabled &&
00685 NC->state() != IsUp
00686 ) {
00687 Log( ( "Append %s for %s\n",
00688 NC->name().latin1(), Interface.latin1() ));
00689 PossibleNetworkSetups.append( NC );
00690 }
00691 }
00692 return PossibleNetworkSetups;
00693 }
00694
00695
00696
00697
00698
00699
00700
00701
00702 bool NetworkSettingsData::canStart( const QString & Interface ) {
00703
00704 NetworkSetup * NC = 0;
00705 QList<NetworkSetup> PossibleNetworkSetups;
00706
00707 PossibleNetworkSetups = collectPossible( Interface );
00708
00709 Log( ( "for %s : Possiblilies %d\n",
00710 Interface.latin1(), PossibleNetworkSetups.count() ));
00711 switch( PossibleNetworkSetups.count() ) {
00712 case 0 :
00713 break;
00714 case 1 :
00715 NC = PossibleNetworkSetups.first();
00716 break;
00717 default :
00718 return 1;
00719 }
00720
00721 if( NC ) {
00722 switch( NC->state() ) {
00723 case Unchecked :
00724 case Unknown :
00725 case Unavailable :
00726 case Disabled :
00727
00728
00729 break;
00730 case Off :
00731
00732 { QString S= NC->setState( Activate );
00733 if( ! S.isEmpty() ) {
00734
00735 Log(( "disallow %ld for %s : %s\n",
00736 NC->number(), Interface.latin1(), S.latin1() ));
00737 break;
00738 }
00739
00740 }
00741
00742 case Available :
00743 case IsUp :
00744
00745 Log(( "allow %ld for %s\n", NC->number(), Interface.latin1()));
00746 printf( "A%d%s\n", NC->number(), Interface.latin1() );
00747 return 0;
00748 }
00749 }
00750
00751
00752 Log(( "disallow %s\n", Interface.latin1()));
00753 printf( "D-%s\n", Interface.latin1() );
00754 return 0;
00755 }
00756
00757 bool NetworkSettingsData::isModified( void ) {
00758 if( ForceModified )
00759 return 1;
00760
00761 for( QDictIterator<NetworkSetup> it(NSResources->networkSetups());
00762 it.current();
00763 ++it ) {
00764 if( it.current()->isModified() ) {
00765 return 1;
00766 }
00767 }
00768 return 0;
00769 }
00770
00771 bool NetworkSettingsData::couldBeTriggered( const QString & Interface ) {
00772
00773 QList<NetworkSetup> PossibleTriggered;
00774
00775 PossibleTriggered = collectTriggered( Interface );
00776
00777 Log( ( "for %s : Possiblilies %d\n",
00778 Interface.latin1(), PossibleTriggered.count() ));
00779
00780 return ( PossibleTriggered.count() ) ? 1 : 0;
00781 }
00782
00783 QList<NetworkSetup> NetworkSettingsData::collectTriggered(
00784 const QString & Interface ) {
00785
00786
00787 NetworkSetup * NC;
00788 QList<NetworkSetup> PossibleTriggered;
00789
00790
00791 Name2NetworkSetup_t & M = NSResources->networkSetups();
00792
00793 for( QDictIterator<NetworkSetup> it(M);
00794 it.current();
00795 ++it ) {
00796 NC = it.current();
00797
00798 if( NC->triggeredBy( Interface ) &&
00799 NC->state() != Disabled &&
00800 NC->state() != IsUp
00801 ) {
00802 Log( ( "Append %s for %s\n",
00803 NC->name().latin1(), Interface.latin1() ));
00804 PossibleTriggered.append( NC );
00805 }
00806 }
00807 return PossibleTriggered;
00808 }
00809
00810 bool NetworkSettingsData::createPath( const QStringList & SL ) {
00811
00812 QDir D( SL[0] );
00813
00814 for ( QStringList::ConstIterator it = SL.begin();
00815 it != SL.end();
00816 ++it ) {
00817
00818 printf( "Create %s\n", (*it).latin1() );
00819 if( it == SL.begin() )
00820 continue;
00821
00822 if( ! D.exists( *it ) ) {
00823 if( ! D.mkdir( *it ) ) {
00824 printf( "Failed %s %s\n", D.path().latin1(), (*it).latin1() );
00825 return 0;
00826 }
00827 }
00828
00829 D.cd( *it );
00830 }
00831 return 1;
00832 }