1

私はobj-Cを学ぶのに苦労していて、助けを借りることができます。暗号化されたDMGを作成し、含まれているファイルを安全に削除するための「コマンドラインツール」を作成しています。hdiutilがDMGを作成すると、暗号化用のパスワードを要求され、このパスワードをbin/echoからhdiutilにパイプしようとしています。

DMGは期待どおりに作成されますが、マウントしようとするとパスワードが受け入れられません。空白のパスワードと最後に余分なスペースの両方を使用してマウントしようとしました。

パイプから値をNSLogすると、正しいように見えますが、これはおそらく最初の4文字を読み取ったためです。パスワードに余分な文字が追加されていると思いますが、その理由と内容がわかりません。

2つの質問1:「正しい」値をパスワードとしてNSTaskpasswordCmdからNSTaskbackupCmdにパイプするにはどうすればよいですか。

2:[backupCmd setStandardInput:pipe]に渡されるのとまったく同じ値をパイプからNSLogするにはどうすればよいですか。

#import <Foundation/Foundation.h>

int main(int argc, const char * argv[])
{

    @autoreleasepool {
        NSTask *passwordCmd = [NSTask new];
        NSTask *backupCmd = [NSTask new];

        NSPipe *pipe;
        pipe = [NSPipe pipe];

        // Enter password by calling echo with a NStask
        [passwordCmd setLaunchPath:@"/bin/echo"];
        [passwordCmd setStandardOutput:pipe]; // write to pipe
        [passwordCmd setArguments: [NSArray arrayWithObjects: @"test", nil]];
        [passwordCmd launch];
        [passwordCmd waitUntilExit];

        // Log the value of the pipe for debugging 
        NSData *output = [[pipe fileHandleForReading] readDataOfLength:4];
        NSString *string = [[NSString alloc] initWithData:output encoding:NSUTF8StringEncoding];
        NSLog(@"'%@'", string);

        // Create a encrypted DMG based on a folder
        [backupCmd setLaunchPath:@"/usr/bin/hdiutil"];
        [backupCmd setCurrentDirectoryPath:@"/Volumes/Macintosh HD/Users/kalle/Desktop/test/"];
        [backupCmd setArguments:[NSArray arrayWithObjects:@"create",@"-format",@"UDZO",@"-srcfolder",@"backup",@"/Volumes/Macintosh HD/Users/kalle/Desktop/backup.dmg",@"-encryption",@"AES-256",@"-stdinpass",@"-quiet",nil]];
        [backupCmd setStandardInput:pipe]; // read from pipe
        [backupCmd launch];
        [backupCmd waitUntilExit];

        // Do some more stuff...

    }
    return 0;
}

どんな助けでも大歓迎です!

4

2 に答える 2

3

コードに2つの問題があります。

1)「hdiutil」ドキュメントには次のように記載されています。

-stdinpass
は、標準入力からnullで終了するパスフレーズを読み取ります。...パスワードにはNULLの前に改行が含まれることに注意してください。

ただし、「/ bin/echo」は常に出力に改行を追加します。したがって、パスワードは「test\n」に設定されます。

2)ログ記録のためにパイプからパスワードを読み取った場合、データは「なくなった」ため、バックアップタスクによって読み取られなくなります。(編集:これは私がこの答えを書いている間にRamy Al Zuhouryによっても投稿されました!)

「/bin/ echo」タスクを使用して、パスワードをバックアップタスクにパイプすることはしません。必要なデータをパイプに直接書き込む方がよいでしょう。

NSString *passwd = @"test\0\n"; // password + NULL character + newline
NSData *passwdData = [passwd dataUsingEncoding:NSUTF8StringEncoding];
[[pipe fileHandleForWriting] writeData:passwdData];
[[pipe fileHandleForWriting] closeFile];

(「hdiutil」が本当にNULL文字の後に改行を期待するかどうかはわかりません。改行なしで試すこともできます。)

于 2013-01-06T19:02:51.583 に答える
1

あなたはすでにパイプから文字を読んでいます、それはとても「消費されている」ので、次にそれらを読むとき、あなたはもうそれらを見つけることができません。

この行を削除すると、それを実行できるはずです。

NSData *output = [[pipe fileHandleForReading] readDataOfLength:4];

パイプで4文字がまだ利用できるようにしています。

于 2013-01-06T18:54:04.377 に答える