Revision: 2969
          http://skim-app.svn.sourceforge.net/skim-app/?rev=2969&view=rev
Author:   hofman
Date:     2007-09-21 13:12:38 -0700 (Fri, 21 Sep 2007)

Log Message:
-----------
Handle password saving for PDFs in the document. Also try to save the password 
when setting the password from the password sheet.

Modified Paths:
--------------
    trunk/SKDocument.h
    trunk/SKDocument.m
    trunk/SKMainWindowController.m
    trunk/SKPDFView.m

Modified: trunk/SKDocument.h
===================================================================
--- trunk/SKDocument.h  2007-09-21 19:14:48 UTC (rev 2968)
+++ trunk/SKDocument.h  2007-09-21 20:12:38 UTC (rev 2969)
@@ -106,6 +106,8 @@
 
 - (NSArray *)fileIDStrings;
 
+- (void)savePasswordInKeychain:(NSString *)password;
+
 - (NSDictionary *)currentDocumentSetup;
 
 - (SKPDFSynchronizer *)synchronizer;

Modified: trunk/SKDocument.m
===================================================================
--- trunk/SKDocument.m  2007-09-21 19:14:48 UTC (rev 2968)
+++ trunk/SKDocument.m  2007-09-21 20:12:38 UTC (rev 2969)
@@ -65,6 +65,7 @@
 #import "NSData_SKExtensions.h"
 #import "SKProgressController.h"
 #import "NSView_SKExtensions.h"
+#import <Security/Security.h>
 
 #define BUNDLE_DATA_FILENAME @"data"
 
@@ -85,6 +86,8 @@
 - (void)setPDFDoc:(PDFDocument *)doc;
 - (void)setNoteDicts:(NSArray *)array;
 
+- (void)tryToUnlockDocument:(PDFDocument *)document;
+
 - (void)checkFileUpdatesIfNeeded;
 - (void)stopCheckingFileUpdates;
 - (void)handleFileUpdateNotification:(NSNotification *)notification;
@@ -125,6 +128,9 @@
 - (void)windowControllerDidLoadNib:(NSWindowController *)aController{
     SKMainWindowController *mainController =  (SKMainWindowController 
*)aController;
     
+    if ([pdfDocument isLocked])
+        [self tryToUnlockDocument:pdfDocument];
+    
     if ([pdfDocument pageCount]) {
         PDFPage *page = [pdfDocument pageAtIndex:0];
         NSPrintInfo *printInfo = [self printInfo];
@@ -1437,6 +1443,80 @@
     return [[self mainWindowController] snapshots];
 }
 
+#pragma mark Passwords
+
+- (void)savePasswordInKeychain:(NSString *)password {
+    int saveOption = [[NSUserDefaults standardUserDefaults] 
integerForKey:SKSavePasswordOptionKey];
+    if ([[self pdfDocument] isLocked] == NO && saveOption != 
NSAlertAlternateReturn) {
+        NSArray *fileIDStrings = [self fileIDStrings];
+        NSString *fileIDString = [fileIDStrings count] ? [fileIDStrings 
objectAtIndex:0] : nil;
+        if (fileIDString) {
+            if (saveOption == NSAlertOtherReturn) {
+                NSAlert *alert = [NSAlert alertWithMessageText:[NSString 
stringWithFormat:NSLocalizedString(@"Remember Password?", @"Message in alert 
dialog")]
+                                                 
defaultButton:NSLocalizedString(@"Yes", @"Button title")
+                                               
alternateButton:NSLocalizedString(@"No", @"Button title")
+                                                   otherButton:nil
+                                     
informativeTextWithFormat:NSLocalizedString(@"Do you want to save this password 
in your Keychain?", @"Informative text in alert dialog")];
+                saveOption = [alert runModal];
+            }
+            if (saveOption == NSAlertDefaultReturn) {
+                const char *userNameCString = [NSUserName() UTF8String];
+                const char *nameCString = [[NSString stringWithFormat:@"Skim - 
%@", fileIDString] UTF8String];
+                
+                OSStatus err;
+                SecKeychainItemRef itemRef = NULL;    
+                const void *passwordData = NULL;
+                UInt32 passwordLength = 0;
+                
+                // first see if the password exists in the keychain
+                err = SecKeychainFindGenericPassword(NULL, 
strlen(nameCString), nameCString, strlen(userNameCString), userNameCString, 
&passwordLength, (void **)&passwordData, &itemRef);
+                
+                if(err == noErr){
+                    // password was on keychain, so flush the buffer and then 
modify the keychain
+                    SecKeychainItemFreeContent(NULL, (void *)passwordData);
+                    passwordData = NULL;
+                    
+                    passwordData = [password UTF8String];
+                    SecKeychainAttribute attrs[] = {
+                        { kSecAccountItemAttr, strlen(userNameCString), (char 
*)userNameCString },
+                        { kSecServiceItemAttr, strlen(nameCString), (char 
*)nameCString } };
+                    const SecKeychainAttributeList attributes = { 
sizeof(attrs) / sizeof(attrs[0]), attrs };
+                    
+                    err = SecKeychainItemModifyAttributesAndData(itemRef, 
&attributes, strlen(passwordData), passwordData);
+                } else if(err == errSecItemNotFound){
+                    // password not on keychain, so add it
+                    passwordData = [password UTF8String];
+                    err = SecKeychainAddGenericPassword(NULL, 
strlen(nameCString), nameCString, strlen(userNameCString), userNameCString, 
strlen(passwordData), passwordData, &itemRef);    
+                } else 
+                    NSLog(@"Error %d occurred setting password", err);
+            }
+        }
+    }
+}
+
+- (void)tryToUnlockDocument:(PDFDocument *)document {
+    int saveOption = [[NSUserDefaults standardUserDefaults] 
integerForKey:SKSavePasswordOptionKey];
+    if (saveOption != NSAlertAlternateReturn) {
+        NSArray *fileIDStrings = [self fileIDStrings];
+        NSString *fileIDString = [fileIDStrings count] ? [fileIDStrings 
objectAtIndex:0] : nil;
+        if (fileIDString) {
+            const char *serviceName = [[NSString stringWithFormat:@"Skim - 
%@", fileIDString] UTF8String];
+            const char *userName = [NSUserName() UTF8String];
+            void *passwordData = NULL;
+            UInt32 passwordLength = 0;
+            NSData *data = nil;
+            NSString *password = nil;
+            OSErr err = SecKeychainFindGenericPassword(NULL, 
strlen(serviceName), serviceName, strlen(userName), userName, &passwordLength, 
&passwordData, NULL);
+            if (err == noErr) {
+                data = [NSData dataWithBytes:passwordData 
length:passwordLength];
+                SecKeychainItemFreeContent(NULL, passwordData);
+                password = [[[NSString alloc] initWithData:data 
encoding:NSUTF8StringEncoding] autorelease];
+                [document unlockWithPassword:password];
+            }
+        }
+    }
+}
+
 #pragma mark Scripting support
 
 - (NSArray *)pages {

Modified: trunk/SKMainWindowController.m
===================================================================
--- trunk/SKMainWindowController.m      2007-09-21 19:14:48 UTC (rev 2968)
+++ trunk/SKMainWindowController.m      2007-09-21 20:12:38 UTC (rev 2969)
@@ -1826,8 +1826,11 @@
 }
 
 - (void)passwordSheetDidEnd:(SKPasswordSheetController *)controller 
returnCode:(int)returnCode contextInfo:(void *)contextInfo {
-    if (returnCode == NSOKButton)
+    if (returnCode == NSOKButton) {
         [pdfView takePasswordFrom:[controller textField]];
+        if ([[pdfView document] isLocked] == NO)
+            [[self document] savePasswordInKeychain:[controller stringValue]];
+    }
 }
 
 - (IBAction)password:(id)sender {
@@ -4843,7 +4846,7 @@
     } else if (action == @selector(performFit:)) {
         return [self isFullScreen] == NO && [self isPresentation] == NO;
     } else if (action == @selector(password:)) {
-        return [self isPresentation] == NO && [[self pdfDocument] isEncrypted];
+        return [self isPresentation] == NO && [[self pdfDocument] isLocked];
     } else if (action == @selector(toggleReadingBar:)) {
         if ([[self pdfView] hasReadingBar])
             [menuItem setTitle:NSLocalizedString(@"Hide Reading Bar", @"Menu 
item title")];

Modified: trunk/SKPDFView.m
===================================================================
--- trunk/SKPDFView.m   2007-09-21 19:14:48 UTC (rev 2968)
+++ trunk/SKPDFView.m   2007-09-21 20:12:38 UTC (rev 2969)
@@ -57,7 +57,6 @@
 #import "NSGeometry_SKExtensions.h"
 #import "SKTypeSelectHelper.h"
 #import "OBUtilities.h"
-#import <Security/Security.h>
 
 NSString *SKPDFViewToolModeChangedNotification = 
@"SKPDFViewToolModeChangedNotification";
 NSString *SKPDFViewAnnotationModeChangedNotification = 
@"SKPDFViewAnnotationModeChangedNotification";
@@ -117,8 +116,6 @@
 - (NSCursor *)cursorForEvent:(NSEvent *)theEvent;
 - (void)updateCursor;
 
-- (void)tryToUnlockDocument:(PDFDocument *)document;
-
 @end
 
 #pragma mark -
@@ -453,8 +450,6 @@
 #pragma mark Accessors
 
 - (void)setDocument:(PDFDocument *)document {
-    if ([document isLocked])
-        [self tryToUnlockDocument:document];
     [readingBar release];
     readingBar = nil;
     selectionRect = NSZeroRect;
@@ -3660,29 +3655,6 @@
     [[self cursorForEvent:event] set];
 }
 
-- (void)tryToUnlockDocument:(PDFDocument *)document {
-    int saveOption = [[NSUserDefaults standardUserDefaults] 
integerForKey:SKSavePasswordOptionKey];
-    if (saveOption != NSAlertAlternateReturn) {
-        NSArray *fileIDStrings = [(SKDocument *)[[[self window] 
windowController] document] fileIDStrings];
-        NSString *fileIDString = [fileIDStrings count] ? [fileIDStrings 
objectAtIndex:0] : nil;
-        if (fileIDString) {
-            const char *serviceName = [[NSString stringWithFormat:@"Skim - 
%@", fileIDString] UTF8String];
-            const char *userName = [NSUserName() UTF8String];
-            void *passwordData = NULL;
-            UInt32 passwordLength = 0;
-            NSData *data = nil;
-            NSString *password = nil;
-            OSErr err = SecKeychainFindGenericPassword(NULL, 
strlen(serviceName), serviceName, strlen(userName), userName, &passwordLength, 
&passwordData, NULL);
-            if (err == noErr) {
-                data = [NSData dataWithBytes:passwordData 
length:passwordLength];
-                SecKeychainItemFreeContent(NULL, passwordData);
-                password = [[[NSString alloc] initWithData:data 
encoding:NSUTF8StringEncoding] autorelease];
-                [document unlockWithPassword:password];
-            }
-        }
-    }
-}
-
 @end
 
 #pragma mark Core Graphics extension
@@ -3773,7 +3745,6 @@
 
 @interface PDFDisplayView (SKExtensions)
 - (void)replacementPasswordEntered:(id)sender;
-- (void)savePasswordInKeychain:(NSString *)password;
 @end
 
 @implementation PDFDisplayView (SKExtensions)
@@ -3786,59 +3757,10 @@
 }
 
 - (void)replacementPasswordEntered:(id)sender {
+    SKDocument *document = [[[self window] windowController] document];
     originalPasswordEntered(self, _cmd, sender);
-    [self savePasswordInKeychain:[sender stringValue]];
+    if ([document respondsToSelector:@selector(savePasswordInKeychain:)])
+        [document savePasswordInKeychain:[sender stringValue]];
 }
 
-- (void)savePasswordInKeychain:(NSString *)password {
-    SKDocument *document = [[[self window] windowController] document];
-    int saveOption = [[NSUserDefaults standardUserDefaults] 
integerForKey:SKSavePasswordOptionKey];
-    if ([document isKindOfClass:[SKDocument class]] && [[document pdfDocument] 
isLocked] == NO && saveOption != NSAlertAlternateReturn) {
-        SKDocument *document = [[[self window] windowController] document];
-        NSArray *fileIDStrings = [document fileIDStrings];
-        NSString *fileIDString = [fileIDStrings count] ? [fileIDStrings 
objectAtIndex:0] : nil;
-        if (fileIDString) {
-            if (saveOption == NSAlertOtherReturn) {
-                NSAlert *alert = [NSAlert alertWithMessageText:[NSString 
stringWithFormat:NSLocalizedString(@"Remember Password?", @"Message in alert 
dialog")]
-                                                 
defaultButton:NSLocalizedString(@"Yes", @"Button title")
-                                               
alternateButton:NSLocalizedString(@"No", @"Button title")
-                                                   otherButton:nil
-                                     
informativeTextWithFormat:NSLocalizedString(@"Do you want to save this password 
in your Keychain?", @"Informative text in alert dialog")];
-                saveOption = [alert runModal];
-            }
-            if (saveOption == NSAlertDefaultReturn) {
-                const char *userNameCString = [NSUserName() UTF8String];
-                const char *nameCString = [[NSString stringWithFormat:@"Skim - 
%@", fileIDString] UTF8String];
-                
-                OSStatus err;
-                SecKeychainItemRef itemRef = NULL;    
-                const void *passwordData = NULL;
-                UInt32 passwordLength = 0;
-                
-                // first see if the password exists in the keychain
-                err = SecKeychainFindGenericPassword(NULL, 
strlen(nameCString), nameCString, strlen(userNameCString), userNameCString, 
&passwordLength, (void **)&passwordData, &itemRef);
-                
-                if(err == noErr){
-                    // password was on keychain, so flush the buffer and then 
modify the keychain
-                    SecKeychainItemFreeContent(NULL, (void *)passwordData);
-                    passwordData = NULL;
-                    
-                    passwordData = [password UTF8String];
-                    SecKeychainAttribute attrs[] = {
-                        { kSecAccountItemAttr, strlen(userNameCString), (char 
*)userNameCString },
-                        { kSecServiceItemAttr, strlen(nameCString), (char 
*)nameCString } };
-                    const SecKeychainAttributeList attributes = { 
sizeof(attrs) / sizeof(attrs[0]), attrs };
-                    
-                    err = SecKeychainItemModifyAttributesAndData(itemRef, 
&attributes, strlen(passwordData), passwordData);
-                } else if(err == errSecItemNotFound){
-                    // password not on keychain, so add it
-                    passwordData = [password UTF8String];
-                    err = SecKeychainAddGenericPassword(NULL, 
strlen(nameCString), nameCString, strlen(userNameCString), userNameCString, 
strlen(passwordData), passwordData, &itemRef);    
-                } else 
-                    NSLog(@"Error %d occurred setting password", err);
-            }
-        }
-    }
-}
-
 @end


This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.

-------------------------------------------------------------------------
This SF.net email is sponsored by: Microsoft
Defy all challenges. Microsoft(R) Visual Studio 2005.
http://clk.atdmt.com/MRT/go/vse0120000070mrt/direct/01/
_______________________________________________
Skim-app-commit mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/skim-app-commit

Reply via email to