00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #include "kpgpbase.h"
00020 #include "kpgp.h"
00021
00022 #include <string.h>
00023 #include <assert.h>
00024
00025 #include <QDateTime>
00026
00027 #include <QByteArray>
00028
00029 #include <klocale.h>
00030 #include <kshell.h>
00031 #include <kdebug.h>
00032
00033 #define PGP2 "pgp"
00034
00035 namespace Kpgp {
00036
00037 Base2::Base2()
00038 : Base()
00039 {
00040 }
00041
00042
00043 Base2::~Base2()
00044 {
00045 }
00046
00047
00048 int
00049 Base2::encrypt( Block& block, const KeyIDList& recipients )
00050 {
00051 return encsign( block, recipients, 0 );
00052 }
00053
00054
00055 int
00056 Base2::clearsign( Block& block, const char *passphrase )
00057 {
00058 return encsign( block, KeyIDList(), passphrase );
00059 }
00060
00061
00062 int
00063 Base2::encsign( Block& block, const KeyIDList& recipients,
00064 const char *passphrase )
00065 {
00066 QByteArray cmd;
00067 int exitStatus = 0;
00068
00069 if(!recipients.isEmpty() && passphrase != 0)
00070 cmd = PGP2 " +batchmode +language=en +verbose=1 -seat";
00071 else if(!recipients.isEmpty())
00072 cmd = PGP2 " +batchmode +language=en +verbose=1 -eat";
00073 else if(passphrase != 0)
00074 cmd = PGP2 " +batchmode +language=en +verbose=1 -sat";
00075 else
00076 {
00077 kDebug( 5326 ) <<"kpgpbase: Neither recipients nor passphrase specified.";
00078 return OK;
00079 }
00080
00081 if(passphrase != 0)
00082 cmd += addUserId();
00083
00084 if(!recipients.isEmpty()) {
00085 if(Module::getKpgp()->encryptToSelf())
00086 {
00087 cmd += " 0x";
00088 cmd += Module::getKpgp()->user();
00089 }
00090
00091 for( KeyIDList::ConstIterator it = recipients.begin();
00092 it != recipients.end(); ++it ) {
00093 cmd += " 0x";
00094 cmd += (*it);
00095 }
00096 }
00097 cmd += " -f";
00098
00099 clear();
00100 input = block.text();
00101 exitStatus = run(cmd.data(), passphrase);
00102 if( !output.isEmpty() )
00103 block.setProcessedText( output );
00104 block.setError( error );
00105
00106 if(exitStatus != 0)
00107 status = ERROR;
00108
00109 #if 0
00110
00111
00112
00113 if(!recipients.isEmpty())
00114 {
00115 int index = 0;
00116 bool bad = false;
00117 unsigned int num = 0;
00118 QByteArray badkeys = "";
00119 if (error.contains("Cannot find the public key") )
00120 {
00121 index = 0;
00122 num = 0;
00123 while((index = error.indexOf("Cannot find the public key",index))
00124 != -1)
00125 {
00126 bad = true;
00127 index = error.indexOf('\'',index);
00128 int index2 = error.indexOf('\'',index+1);
00129 if (num++)
00130 badkeys += ", ";
00131 badkeys += error.mid(index, index2-index+1);
00132 }
00133 if(bad)
00134 {
00135 badkeys.trimmed();
00136 if(num == recipients.count())
00137 errMsg = i18n("Could not find public keys matching the userid(s)\n"
00138 "%1;\n"
00139 "the message is not encrypted.",
00140 badkeys.data() );
00141 else
00142 errMsg = i18n("Could not find public keys matching the userid(s)\n"
00143 "%1;\n"
00144 "these persons will not be able to read the message.",
00145 badkeys.data() );
00146 status |= MISSINGKEY;
00147 status |= ERROR;
00148 }
00149 }
00150 if (error.contains("skipping userid") )
00151 {
00152 index = 0;
00153 num = 0;
00154 while((index = error.indexOf("skipping userid",index))
00155 != -1)
00156 {
00157 bad = true;
00158 int index2 = error.indexOf('\n',index+16);
00159 if (num++)
00160 badkeys += ", ";
00161 badkeys += error.mid(index+16, index2-index-16);
00162 index = index2;
00163 }
00164 if(bad)
00165 {
00166 badkeys.trimmed();
00167 if(num == recipients.count())
00168 errMsg = i18n("Public keys not certified with trusted signature "
00169 "for userid(s)\n"
00170 "%1.\n"
00171 "The message is not encrypted.",
00172 badkeys.data() );
00173 else
00174 errMsg = i18n("Public keys not certified with trusted signature "
00175 "for userid(s)\n"
00176 "%1;\n"
00177 "these persons will not be able to read the message.",
00178 badkeys.data() );
00179 status |= BADKEYS;
00180 status |= ERROR;
00181 return status;
00182 }
00183 }
00184 }
00185 #endif
00186 if(passphrase != 0)
00187 {
00188 if(error.contains("Pass phrase is good") )
00189 {
00190
00191 status |= SIGNED;
00192 }
00193 if( error.contains("Bad pass phrase") )
00194 {
00195 errMsg = i18n("Bad passphrase; could not sign.");
00196 status |= BADPHRASE;
00197 status |= ERR_SIGNING;
00198 status |= ERROR;
00199 }
00200 }
00201 if (error.contains("Signature error") )
00202 {
00203 errMsg = i18n("Signing failed: please check your PGP User Identity, "
00204 "the PGP setup, and the key rings.");
00205 status |= NO_SEC_KEY;
00206 status |= ERR_SIGNING;
00207 status |= ERROR;
00208 }
00209 if (error.contains("Encryption error") )
00210 {
00211 errMsg = i18n("Encryption failed: please check your PGP setup "
00212 "and the key rings.");
00213 status |= NO_SEC_KEY;
00214 status |= BADKEYS;
00215 status |= ERROR;
00216 }
00217
00218
00219 block.setStatus( status );
00220 return status;
00221 }
00222
00223
00224 int
00225 Base2::decrypt( Block& block, const char *passphrase )
00226 {
00227 int index, index2;
00228 int exitStatus = 0;
00229
00230 clear();
00231 input = block.text();
00232 exitStatus = run(PGP2 " +batchmode +language=en -f", passphrase);
00233 if( !output.isEmpty() )
00234 block.setProcessedText( output );
00235 block.setError( error );
00236
00237
00238
00239 if(error.contains("ASCII armor corrupted.") )
00240 {
00241 kDebug( 5326 ) <<"removing ASCII armor header";
00242 int index1 = input.indexOf("-----BEGIN PGP SIGNED MESSAGE-----");
00243 if(index1 != -1)
00244 index1 = input.indexOf("-----BEGIN PGP SIGNATURE-----", index1);
00245 else
00246 index1 = input.indexOf("-----BEGIN PGP MESSAGE-----");
00247 index1 = input.indexOf('\n', index1);
00248 index2 = input.indexOf("\n\n", index1);
00249 input.remove(index1, index2 - index1);
00250 exitStatus = run(PGP2 " +batchmode +language=en -f", passphrase);
00251 if( !output.isEmpty() )
00252 block.setProcessedText( output );
00253 block.setError( error );
00254 }
00255
00256 if(exitStatus == -1) {
00257 errMsg = i18n("error running PGP");
00258 status = ERROR;
00259 block.setStatus( status );
00260 return status;
00261 }
00262
00263
00264
00265
00266
00267
00268
00269
00270
00271
00272
00273
00274
00275
00276
00277
00278
00279
00280
00281
00282
00283 if(error.contains("File is encrypted.") )
00284 {
00285
00286 status |= ENCRYPTED;
00287 if((index = error.indexOf("Key for user ID:")) != -1 )
00288 {
00289
00290 index += 17;
00291 index2 = error.indexOf('\n', index);
00292 block.setRequiredUserId( error.mid(index, index2 - index) );
00293
00294
00295 if((passphrase != 0) && (error.contains("Bad pass phrase") ))
00296 {
00297 errMsg = i18n("Bad passphrase; could not decrypt.");
00298 kDebug( 5326 ) <<"Base: passphrase is bad";
00299 status |= BADPHRASE;
00300 status |= ERROR;
00301 }
00302 }
00303 else
00304 {
00305
00306 status |= NO_SEC_KEY;
00307 status |= ERROR;
00308 errMsg = i18n("You do not have the secret key needed to decrypt this message.");
00309 kDebug( 5326 ) <<"Base: no secret key for this message";
00310 }
00311
00312 #if 0
00313
00314
00315 index = error.indexOf("can only be read by:");
00316 if(index != -1)
00317 {
00318 index = error.indexOf('\n',index);
00319 int end = error.indexOf("\n\n",index);
00320
00321 mRecipients.clear();
00322 while( (index2 = error.indexOf('\n',index+1)) <= end )
00323 {
00324 QByteArray item = error.mid(index+1,index2-index-1);
00325 item.trimmed();
00326 mRecipients.append(item);
00327 index = index2;
00328 }
00329 }
00330 #endif
00331 }
00332
00333
00334
00335
00336
00337
00338
00339
00340
00341
00342
00343
00344
00345
00346
00347
00348
00349
00350
00351
00352
00353
00354
00355
00356
00357
00358
00359
00360
00361
00362
00363
00364
00365
00366
00367
00368
00369
00370
00371
00372
00373
00374
00375
00376
00377
00378
00379
00380
00381
00382
00383
00384
00385
00386
00387
00388
00389
00390
00391
00392
00393 if((index = error.indexOf("File has signature")) != -1 )
00394 {
00395
00396 index = error.indexOf('\n', index+18) + 1;
00397
00398 status |= SIGNED;
00399
00400 if ((index2 = error.indexOf("Signature made", index)) != -1 ) {
00401 index2 += 15;
00402 int index3 = error.indexOf("using", index2);
00403 block.setSignatureDate( error.mid(index2, index3-index2-1) );
00404 kDebug( 5326 ) <<"Message was signed on '" << block.signatureDate() <<"'";
00405 index3 = error.indexOf("key ID ", index3) + 7;
00406 block.setSignatureKeyId( error.mid(index3,8) );
00407 kDebug( 5326 ) <<"Message was signed with key '" << block.signatureKeyId() <<"'";
00408 }
00409 else {
00410
00411
00412 block.setSignatureDate( "" );
00413 block.setSignatureKeyId( "" );
00414 }
00415
00416 if( ( index2 = error.indexOf("Key matching expected", index) ) != -1 )
00417 {
00418 status |= UNKNOWN_SIG;
00419 status |= GOODSIG;
00420 int index3 = error.indexOf("Key ID ", index2) + 7;
00421 block.setSignatureKeyId( error.mid(index3,8) );
00422 block.setSignatureUserId( QString() );
00423 }
00424 else if( (index2 = error.indexOf("Good signature from", index)) != -1 )
00425 {
00426 status |= GOODSIG;
00427
00428 index = error.indexOf('"',index2+19);
00429 index2 = error.indexOf('"', index+1);
00430 block.setSignatureUserId( error.mid(index+1, index2-index-1) );
00431 }
00432 else if( (index2 = error.indexOf("Bad signature from", index)) != -1 )
00433 {
00434 status |= ERROR;
00435
00436 index = error.indexOf('"',index2+19);
00437 index2 = error.indexOf('"', index+1);
00438 block.setSignatureUserId( error.mid(index+1, index2-index-1) );
00439 }
00440 else if( error.indexOf("Keyring file", index) != -1 )
00441 {
00442
00443 status |= UNKNOWN_SIG;
00444 status |= GOODSIG;
00445
00446 index = error.indexOf('\'', index) + 1;
00447 index2 = error.indexOf('\'', index);
00448 block.setSignatureUserId( i18n("The keyring file %1 does not exist.\n"
00449 "Please check your PGP setup.", QString::fromLatin1( error.mid(index, index2-index)) ) );
00450 }
00451 else
00452 {
00453 status |= ERROR;
00454 block.setSignatureUserId( i18n("Unknown error") );
00455 }
00456 }
00457
00458 block.setStatus( status );
00459 return status;
00460 }
00461
00462
00463 Key*
00464 Base2::readPublicKey( const KeyID& keyID,
00465 const bool readTrust ,
00466 Key* key )
00467 {
00468 int exitStatus = 0;
00469
00470 status = 0;
00471 exitStatus = run( PGP2 " +batchmode +language=en +verbose=0 -kvc -f 0x" +
00472 keyID, 0, true );
00473
00474 if(exitStatus != 0) {
00475 status = ERROR;
00476 return 0;
00477 }
00478
00479 key = parsePublicKeyData( output, key );
00480
00481 if( key == 0 )
00482 {
00483 return 0;
00484 }
00485
00486 if( readTrust )
00487 {
00488 exitStatus = run( PGP2 " +batchmode +language=en +verbose=0 -kc -f",
00489 0, true );
00490
00491 if(exitStatus != 0) {
00492 status = ERROR;
00493 return 0;
00494 }
00495
00496 parseTrustDataForKey( key, error );
00497 }
00498
00499 return key;
00500 }
00501
00502
00503 KeyList
00504 Base2::publicKeys( const QStringList & patterns )
00505 {
00506 return doGetPublicKeys( PGP2 " +batchmode +language=en +verbose=0 -kvc -f",
00507 patterns );
00508 }
00509
00510 KeyList
00511 Base2::doGetPublicKeys( const QByteArray & cmd, const QStringList & patterns )
00512 {
00513 int exitStatus = 0;
00514 KeyList publicKeys;
00515
00516 status = 0;
00517 if ( patterns.isEmpty() ) {
00518 exitStatus = run( cmd, 0, true );
00519
00520 if ( exitStatus != 0 ) {
00521 status = ERROR;
00522 return KeyList();
00523 }
00524
00525
00526 publicKeys = parseKeyList( output, false );
00527 }
00528 else {
00529 typedef QMap<QByteArray, Key*> KeyMap;
00530 KeyMap map;
00531
00532 for ( QStringList::ConstIterator it = patterns.begin();
00533 it != patterns.end(); ++it ) {
00534 exitStatus = run( cmd + ' ' + KShell::quoteArg( *it ).toLocal8Bit(),
00535 0, true );
00536
00537 if ( exitStatus != 0 ) {
00538 status = ERROR;
00539 return KeyList();
00540 }
00541
00542
00543 publicKeys = parseKeyList( output, false );
00544
00545
00546 while ( !publicKeys.isEmpty() ) {
00547 Key * key = publicKeys.take( 0 );
00548 if ( !map.contains( key->primaryFingerprint() ) )
00549 map.insert( key->primaryFingerprint(), key );
00550 else
00551 delete key;
00552 }
00553 }
00554
00555 for ( KeyMap::ConstIterator it = map.begin(); it != map.end(); ++it ) {
00556 publicKeys.append( it.value() );
00557 }
00558 }
00559
00560
00561 publicKeys.sort();
00562
00563 return publicKeys;
00564 }
00565
00566 KeyList
00567 Base2::secretKeys( const QStringList & patterns )
00568 {
00569 return publicKeys( patterns );
00570 }
00571
00572
00573 int
00574 Base2::signKey(const KeyID& keyID, const char *passphrase)
00575 {
00576 QByteArray cmd;
00577 int exitStatus = 0;
00578
00579 cmd = PGP2 " +batchmode +language=en -ks -f ";
00580 cmd += addUserId();
00581 cmd += " 0x" + keyID;
00582
00583 status = 0;
00584 exitStatus = run(cmd.data(),passphrase);
00585
00586 if (exitStatus != 0)
00587 status = ERROR;
00588
00589 return status;
00590 }
00591
00592
00593 QByteArray Base2::getAsciiPublicKey(const KeyID& keyID)
00594 {
00595 int exitStatus = 0;
00596
00597 if (keyID.isEmpty())
00598 return QByteArray();
00599
00600 status = 0;
00601 exitStatus = run( PGP2 " +batchmode +force +language=en -kxaf 0x" + keyID,
00602 0, true );
00603
00604 if(exitStatus != 0) {
00605 status = ERROR;
00606 return QByteArray();
00607 }
00608
00609 return output;
00610 }
00611
00612
00613 Key*
00614 Base2::parsePublicKeyData( const QByteArray& output, Key* key )
00615 {
00616 Subkey *subkey = 0;
00617 int index;
00618
00619
00620 if( !strncmp( output.data(), "pub", 3 ) ||
00621 !strncmp( output.data(), "sec", 3 ) )
00622 index = 0;
00623 else
00624 {
00625
00626
00627
00628
00629
00630 index = output.indexOf( "\npub" );
00631 if( index == -1 )
00632 return 0;
00633 else
00634 index++;
00635 }
00636
00637 while( true )
00638 {
00639 int index2;
00640
00641
00642 if( ( index2 = output.indexOf( '\n', index ) ) == -1 )
00643 break;
00644
00645 if( !strncmp( output.data() + index, "pub", 3 ) ||
00646 !strncmp( output.data() + index, "sec", 3 ) )
00647 {
00648
00649
00650
00651
00652
00653
00654
00655
00656
00657 int pos, pos2;
00658
00659 if( key == 0 )
00660 key = new Key();
00661 else
00662 key->clear();
00663
00664
00665 key->setCanEncrypt( true );
00666 key->setCanSign( true );
00667 key->setCanCertify( true );
00668
00669
00670 subkey = new Subkey( "", false );
00671 key->addSubkey( subkey );
00672
00673 subkey->setCanEncrypt( true );
00674 subkey->setCanSign( true );
00675 subkey->setCanCertify( true );
00676
00677 subkey->setExpirationDate( -1 );
00678
00679
00680 switch( output[index+3] )
00681 {
00682 case ' ':
00683 break;
00684 case '-':
00685 subkey->setDisabled( true );
00686 key->setDisabled( true );
00687 break;
00688 case '>':
00689 subkey->setExpired( true );
00690 key->setExpired( true );
00691 break;
00692 default:
00693 kDebug( 5326 ) <<"Unknown key flag.";
00694 }
00695
00696
00697 pos = index + 4;
00698 while( output[pos] == ' ' )
00699 pos++;
00700 pos2 = output.indexOf( '/', pos );
00701 subkey->setKeyLength( output.mid( pos, pos2-pos ).toUInt() );
00702
00703
00704 pos = pos2 + 1;
00705 pos2 = output.indexOf( ' ', pos );
00706 subkey->setKeyID( output.mid( pos, pos2-pos ) );
00707
00708
00709 pos = pos2 + 1;
00710 while( output[pos] == ' ' )
00711 pos++;
00712 pos2 = output.indexOf( ' ', pos );
00713 int year = output.mid( pos, 4 ).toInt();
00714 int month = output.mid( pos+5, 2 ).toInt();
00715 int day = output.mid( pos+8, 2 ).toInt();
00716 QDateTime dt( QDate( year, month, day ), QTime( 00, 00 ) );
00717 QDateTime epoch( QDate( 1970, 01, 01 ), QTime( 00, 00 ) );
00718
00719
00720
00721
00722 subkey->setCreationDate( epoch.secsTo( dt ) );
00723
00724
00725 pos = pos2 + 1;
00726 while( output[pos] == ' ' )
00727 pos++;
00728 QByteArray uid = output.mid( pos, index2-pos );
00729 if( uid != "*** KEY REVOKED ***" )
00730 key->addUserID( uid );
00731 else
00732 {
00733 subkey->setRevoked( true );
00734 key->setRevoked( true );
00735 }
00736 }
00737 else if( output[index] == ' ' )
00738 {
00739
00740 if( key == 0 )
00741 break;
00742 assert( subkey != 0 );
00743
00744 int pos = index + 1;
00745 while( output[pos] == ' ' )
00746 pos++;
00747
00748 if( !strncmp( output.data() + pos, "Key fingerprint = ", 18 ) )
00749 {
00750
00751
00752
00753 QByteArray fingerprint = output.mid( pos, index2-pos );
00754
00755 for ( int idx = 0 ; (idx = fingerprint.indexOf(' ', idx)) != -1 ; )
00756 fingerprint.replace( idx, 1, "" );
00757
00758 subkey->setFingerprint( fingerprint );
00759 }
00760 else if( !strncmp( output.data() + pos, "Expire: ", 8 ) ||
00761 !strncmp( output.data() + pos, "no expire ", 10 ) )
00762 {
00763
00764
00765
00766
00767
00768 if( output[pos] == 'E' )
00769 {
00770
00771 pos += 8;
00772 int year = output.mid( pos, 4 ).toInt();
00773 int month = output.mid( pos+5, 2 ).toInt();
00774 int day = output.mid( pos+8, 2 ).toInt();
00775 QDateTime dt( QDate( year, month, day ), QTime( 00, 00 ) );
00776 QDateTime epoch( QDate( 1970, 01, 01 ), QTime( 00, 00 ) );
00777
00778 subkey->setExpirationDate( epoch.secsTo( dt ) );
00779 pos += 11;
00780 }
00781 else
00782 pos += 10;
00783
00784
00785 if( pos != index2 )
00786 {
00787 if( !strncmp( output.data() + pos, "SIGNature only", 14 ) )
00788 {
00789 subkey->setCanEncrypt( false );
00790 key->setCanEncrypt( false );
00791 }
00792 else if( !strncmp( output.data() + pos, "ENCRyption only", 15 ) )
00793 {
00794 subkey->setCanSign( false );
00795 key->setCanSign( false );
00796 subkey->setCanCertify( false );
00797 key->setCanCertify( false );
00798 }
00799 }
00800 }
00801 else
00802 {
00803
00804
00805
00806 key->addUserID( output.mid( pos, index2-pos ) );
00807 }
00808 }
00809 index = index2 + 1;
00810 }
00811
00812
00813
00814 return key;
00815 }
00816
00817
00818 void
00819 Base2::parseTrustDataForKey( Key* key, const QByteArray& str )
00820 {
00821 if( ( key == 0 ) || str.isEmpty() )
00822 return;
00823
00824 QByteArray keyID = key->primaryKeyID();
00825 UserIDList userIDs = key->userIDs();
00826
00827
00828 int index = str.indexOf( '\n' ) + 1;
00829 while( ( index > 0 ) &&
00830 ( strncmp( str.data() + index+2, keyID.data(), 8 ) != 0 ) )
00831 index = str.indexOf( '\n', index ) + 1;
00832
00833 if( index == 0 )
00834 return;
00835
00836 bool ultimateTrust = false;
00837 if( !strncmp( str.data() + index+11, "ultimate", 8 ) )
00838 ultimateTrust = true;
00839
00840 bool firstLine = true;
00841
00842 while( true )
00843 {
00844 int index2;
00845
00846
00847 if( ( index2 = str.indexOf( '\n', index ) ) == -1 )
00848 break;
00849
00850
00851 if( !firstLine && ( str[index+2] != ' ' ) )
00852 break;
00853
00854 if( str[index+21] != ' ' )
00855 {
00856
00857
00858 Validity validity = KPGP_VALIDITY_UNKNOWN;
00859 if( !strncmp( str.data() + index+21, "complete", 8 ) )
00860 if( ultimateTrust )
00861 validity = KPGP_VALIDITY_ULTIMATE;
00862 else
00863 validity = KPGP_VALIDITY_FULL;
00864 else if( !strncmp( str.data() + index+21, "marginal", 8 ) )
00865 validity = KPGP_VALIDITY_MARGINAL;
00866 else if( !strncmp( str.data() + index+21, "never", 5 ) )
00867 validity = KPGP_VALIDITY_NEVER;
00868 else if( !strncmp( str.data() + index+21, "undefined", 9 ) )
00869 validity = KPGP_VALIDITY_UNDEFINED;
00870
00871
00872 int pos = index + 31;
00873 if( str[index+2] == ' ' )
00874 pos++;
00875 QString uid = str.mid( pos, index2-pos );
00876
00877
00878 for( UserIDListIterator it( userIDs ); it.current(); ++it )
00879 if( (*it)->text() == uid )
00880 {
00881 kDebug( 5326 )<<"Setting the validity of"<<uid<<" to"<<validity;
00882 (*it)->setValidity( validity );
00883 break;
00884 }
00885 }
00886
00887 firstLine = false;
00888 index = index2 + 1;
00889 }
00890 }
00891
00892
00893 KeyList
00894 Base2::parseKeyList( const QByteArray& output, bool secretKeys )
00895 {
00896 kDebug( 5326 ) <<"Kpgp::Base2::parseKeyList()";
00897 KeyList keys;
00898 Key *key = 0;
00899 Subkey *subkey = 0;
00900 int index;
00901
00902
00903 if( !strncmp( output.data(), "pub", 3 ) ||
00904 !strncmp( output.data(), "sec", 3 ) )
00905 index = 0;
00906 else
00907 {
00908 if( secretKeys )
00909 index = output.indexOf( "\nsec" );
00910 else
00911 index = output.indexOf( "\npub" );
00912 if( index == -1 )
00913 return keys;
00914 else
00915 index++;
00916 }
00917
00918 while( true )
00919 {
00920 int index2;
00921
00922
00923 if( ( index2 = output.indexOf( '\n', index ) ) == -1 )
00924 break;
00925
00926 if( !strncmp( output.data() + index, "pub", 3 ) ||
00927 !strncmp( output.data() + index, "sec", 3 ) )
00928 {
00929
00930
00931
00932
00933
00934
00935
00936
00937
00938 int pos, pos2;
00939
00940 if( key != 0 )
00941 keys.append( key );
00942
00943 key = new Key();
00944 key->setSecret( secretKeys );
00945
00946 key->setCanEncrypt( true );
00947 key->setCanSign( true );
00948 key->setCanCertify( true );
00949
00950 subkey = new Subkey( "", secretKeys );
00951 key->addSubkey( subkey );
00952
00953 subkey->setCanEncrypt( true );
00954 subkey->setCanSign( true );
00955 subkey->setCanCertify( true );
00956
00957 subkey->setExpirationDate( -1 );
00958
00959
00960 switch( output[index+3] )
00961 {
00962 case ' ':
00963 break;
00964 case '-':
00965 subkey->setDisabled( true );
00966 key->