1
- using System ;
1
+ /*
2
+ * Keenou
3
+ * Copyright (C) 2015 Charles Munson
4
+ *
5
+ * This program is free software; you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation; either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License along
16
+ * with this program; if not, write to the Free Software Foundation, Inc.,
17
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18
+ */
19
+
20
+ using System ;
2
21
using System . Windows . Forms ;
3
22
using System . Security . Principal ;
4
23
using System . IO ;
@@ -211,6 +230,9 @@ private void b_encrypt_Click(object sender, EventArgs e)
211
230
212
231
213
232
// Generate master key & protect with user password //
233
+ l_statusLabel . Text = "Generating encryption key ..." ;
234
+ Application . DoEvents ( ) ;
235
+
214
236
string masterKey = null ;
215
237
string encMasterKey = null ;
216
238
try
@@ -234,74 +256,124 @@ private void b_encrypt_Click(object sender, EventArgs e)
234
256
235
257
236
258
237
- // Create new encrypted volume //
238
- l_statusLabel . Text = "Creating encrypted volume ..." ;
239
- Application . DoEvents ( ) ;
240
- res = EncryptHome . CreateEncryptedVolume ( hashChosen , t_volumeLoc . Text , targetDrive , masterKey , cipherChosen , volSize ) ;
241
- if ( res == null || ! res . Success )
259
+
260
+ // Run work-heavy tasks in a separate thread
261
+ CancellationTokenSource cts = new CancellationTokenSource ( ) ;
262
+ CancellationToken cancelToken = cts . Token ;
263
+ var workerThread = Task . Factory . StartNew ( ( ) =>
242
264
{
243
- ReportEncryptHomeError ( res ) ;
244
- return ;
245
- }
246
- // * //
247
265
266
+ // Update UI
267
+ this . Invoke ( ( MethodInvoker ) delegate
268
+ {
269
+ s_progress . Value = 25 ;
270
+ l_statusLabel . Text = "Creating encrypted volume ..." ;
271
+ Application . DoEvents ( ) ;
272
+ s_progress . ProgressBar . Refresh ( ) ;
273
+ } ) ;
274
+
275
+ // Create new encrypted volume //
276
+ res = EncryptHome . CreateEncryptedVolume ( hashChosen , t_volumeLoc . Text , targetDrive , masterKey , cipherChosen , volSize ) ;
277
+ if ( res == null || ! res . Success )
278
+ {
279
+ return res ;
280
+ }
281
+ // * //
248
282
249
283
250
- // Mount home folder's encrypted file as targetDrive //
251
- s_progress . Value = 33 ;
252
- l_statusLabel . Text = "Mounting encrypted volume ..." ;
253
- Application . DoEvents ( ) ;
254
- s_progress . ProgressBar . Refresh ( ) ;
255
- res = EncryptHome . MountEncryptedVolume ( hashChosen , t_volumeLoc . Text , targetDrive , masterKey ) ;
256
- if ( res == null || ! res . Success )
257
- {
258
- ReportEncryptHomeError ( res ) ;
259
- return ;
260
- }
261
- // * //
262
284
285
+ // Update UI
286
+ this . Invoke ( ( MethodInvoker ) delegate
287
+ {
288
+ s_progress . Value = 50 ;
289
+ l_statusLabel . Text = "Mounting encrypted volume ..." ;
290
+ Application . DoEvents ( ) ;
291
+ s_progress . ProgressBar . Refresh ( ) ;
292
+ } ) ;
293
+
294
+ // Mount home folder's encrypted file as targetDrive //
295
+ res = EncryptHome . MountEncryptedVolume ( hashChosen , t_volumeLoc . Text , targetDrive , masterKey ) ;
296
+ if ( res == null || ! res . Success )
297
+ {
298
+ return res ;
299
+ }
300
+ // * //
263
301
264
302
265
- // Copy everything over from home directory to encrypted container //
266
- s_progress . Value = 66 ;
267
- l_statusLabel . Text = "Copying home directory to encrypted container ..." ;
268
- Application . DoEvents ( ) ;
269
- s_progress . ProgressBar . Refresh ( ) ;
270
- res = EncryptHome . CopyDataFromHomeFolder ( this . homeFolder , targetDrive ) ;
271
- if ( res == null || ! res . Success )
303
+
304
+ // Update UI
305
+ this . Invoke ( ( MethodInvoker ) delegate
306
+ {
307
+ s_progress . Value = 75 ;
308
+ l_statusLabel . Text = "Copying home directory to encrypted container ..." ;
309
+ Application . DoEvents ( ) ;
310
+ s_progress . ProgressBar . Refresh ( ) ;
311
+ } ) ;
312
+
313
+ // Copy everything over from home directory to encrypted container //
314
+ res = EncryptHome . CopyDataFromHomeFolder ( this . homeFolder , targetDrive ) ;
315
+ if ( res == null || ! res . Success )
316
+ {
317
+ return res ;
318
+ }
319
+ // * //
320
+
321
+
322
+
323
+ // TODO: Unmount encrypted volume (after beta testing over)
324
+ // VeraCrypt should auto-unmount, but we'll do it manually to be sure
325
+
326
+
327
+
328
+ return new BooleanResult ( ) { Success = true } ;
329
+
330
+ } , TaskCreationOptions . LongRunning ) ;
331
+
332
+
333
+
334
+ // When threaded tasks finish, check for errors and continue (if appropriate)
335
+ workerThread . ContinueWith ( ( antecedent ) =>
272
336
{
273
- ReportEncryptHomeError ( res ) ;
274
- return ;
275
- }
276
- // * //
337
+ // Block until we get a result back from previous thread
338
+ BooleanResult result = antecedent . Result ;
277
339
278
340
341
+ // Check if there was an error in previous thread
342
+ if ( result == null || ! result . Success )
343
+ {
344
+ ReportEncryptHomeError ( result ) ;
345
+ return ;
346
+ }
279
347
280
- // TODO: Unmount encrypted volume (after beta testing over)
281
- // VeraCrypt should auto-unmount, but we'll do it manually to be sure
282
348
283
349
350
+ // Set necessary registry values //
351
+ Registry . SetValue ( @"HKEY_LOCAL_MACHINE\SOFTWARE\Keenou\" + this . usrSID , "encContainerLoc" , t_volumeLoc . Text ) ;
352
+ Registry . SetValue ( @"HKEY_LOCAL_MACHINE\SOFTWARE\Keenou\" + this . usrSID , "firstBoot" , true , RegistryValueKind . DWord ) ;
353
+ Registry . SetValue ( @"HKEY_LOCAL_MACHINE\SOFTWARE\Keenou\" + this . usrSID , "hash" , hashChosen ) ;
354
+ Registry . SetValue ( @"HKEY_LOCAL_MACHINE\SOFTWARE\Keenou\" + this . usrSID , "encHeader" , encMasterKey ) ;
355
+ // * //
284
356
285
- // Set necessary registry values //
286
- Registry . SetValue ( @"HKEY_LOCAL_MACHINE\SOFTWARE\Keenou\" + this . usrSID , "encContainerLoc" , t_volumeLoc . Text ) ;
287
- Registry . SetValue ( @"HKEY_LOCAL_MACHINE\SOFTWARE\Keenou\" + this . usrSID , "firstBoot" , true , RegistryValueKind . DWord ) ;
288
- Registry . SetValue ( @"HKEY_LOCAL_MACHINE\SOFTWARE\Keenou\" + this . usrSID , "hash" , hashChosen ) ;
289
- Registry . SetValue ( @"HKEY_LOCAL_MACHINE\SOFTWARE\Keenou\" + this . usrSID , "encHeader" , encMasterKey ) ;
290
- // * //
291
357
292
358
359
+ // Re-enable everything //
360
+ this . Cursor = Cursors . Default ;
361
+ l_statusLabel . Text = "Log out and back in to finish ..." ;
362
+ s_progress . Value = 100 ;
363
+ Application . DoEvents ( ) ;
364
+ // * //
293
365
294
- // Re-enable everything //
295
- this . Cursor = Cursors . Default ;
296
- l_statusLabel . Text = "Log out and back in to finish ..." ;
297
- s_progress . Value = 100 ;
298
- Application . DoEvents ( ) ;
299
- // * //
300
366
301
367
368
+ // Inform user of the good news
369
+ MessageBox . Show ( "Almost done! You must log out and log back in via Keenou-pGina to finish the migration!" ) ;
370
+
371
+ } ,
372
+ cancelToken ,
373
+ TaskContinuationOptions . OnlyOnRanToCompletion ,
374
+ TaskScheduler . FromCurrentSynchronizationContext ( )
375
+ ) ;
302
376
303
- // Inform user of the good news
304
- MessageBox . Show ( "Almost done! You must log out and log back in via Keenou-pGina to finish the migration!" ) ;
305
377
}
306
378
// * //
307
379
@@ -349,15 +421,33 @@ private void b_setVolumeSize_Click(object sender, EventArgs e)
349
421
Application . DoEvents ( ) ;
350
422
351
423
352
- // Determine free space on enc volume target drive
353
- long targetSpace = Toolbox . GetAvailableFreeSpace ( t_volumeLoc . Text ) ;
354
-
355
-
356
424
// Do calculation of current size (if not already done)
357
425
if ( this . homeDirSize <= 0 )
358
426
{
359
- this . homeDirSize = Toolbox . GetDirectorySize ( this . homeFolder ) ;
427
+ var taskA = Task . Factory . StartNew ( ( ) => Toolbox . GetDirectorySize ( this . homeFolder ) , TaskCreationOptions . LongRunning ) ;
428
+ CancellationTokenSource cts = new CancellationTokenSource ( ) ;
429
+ CancellationToken cancelToken = cts . Token ;
430
+
431
+ taskA . ContinueWith ( ( antecedent ) =>
432
+ {
433
+ this . homeDirSize = antecedent . Result ;
434
+ this . b_setVolumeSize_Click_Callback ( ) ;
435
+ } ,
436
+ cancelToken ,
437
+ TaskContinuationOptions . OnlyOnRanToCompletion ,
438
+ TaskScheduler . FromCurrentSynchronizationContext ( )
439
+ ) ;
440
+ }
441
+ else
442
+ {
443
+ this . b_setVolumeSize_Click_Callback ( ) ;
360
444
}
445
+ }
446
+
447
+ private void b_setVolumeSize_Click_Callback ( )
448
+ {
449
+ // Determine free space on enc volume target drive
450
+ long targetSpace = Toolbox . GetAvailableFreeSpace ( t_volumeLoc . Text ) ;
361
451
362
452
363
453
// Show suggested volume size
0 commit comments