2013-02-18

C# AES-256-CBC 加解密

使用到的名稱空間 :
using System;
using System.Text;
using System.Security.Cryptography;
using System.IO;

程式碼如下,將字串 "text to be encrypted" 加密後解密看結果是否相同 :
RijndaelManaged rijalg = new RijndaelManaged();
 
//-----------------
//設定 cipher 格式 AES-256-CBC
rijalg.BlockSize = 128;
rijalg.KeySize = 256;
rijalg.FeedbackSize = 128;
rijalg.Padding = PaddingMode.PKCS7;
rijalg.Mode = CipherMode.CBC;
 
rijalg.Key = (new SHA256Managed()).ComputeHash(Encoding.ASCII.GetBytes("IHazSekretKey"));
rijalg.IV = System.Text.Encoding.ASCII.GetBytes("1234567890123456");
 
//-----------------
//加密
ICryptoTransform encryptor =rijalg.CreateEncryptor(rijalg.Key, rijalg.IV);
 
byte[] encrypted;
// Create the streams used for encryption.
using (MemoryStream msEncrypt = new MemoryStream())
{
    using (CryptoStream csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
    {
        using (StreamWriter swEncrypt = new StreamWriter(csEncrypt))
        {
            //Write all data to the stream.
            swEncrypt.Write("text to be encrypted");
        }
        encrypted = msEncrypt.ToArray();
    }
}
 
//-----------------
//加密後的 base64 字串 :
//eiLbdhFSFrDqvUJmjbUgwD8REjBRoRWWwHHImmMLNZA=
System.Console.WriteLine(Convert.ToBase64String(encrypted));
 
//-----------------
//解密
ICryptoTransform decryptor = rijalg.CreateDecryptor(rijalg.Key, rijalg.IV);
 
string plaintext;
// Create the streams used for decryption. 
using (MemoryStream msDecrypt = new MemoryStream(encrypted))
{
    using (CryptoStream csDecrypt = new CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read))
    {
        using (StreamReader srDecrypt = new StreamReader(csDecrypt))
        {
 
            // Read the decrypted bytes from the decrypting stream 
            // and place them in a string.
            plaintext = srDecrypt.ReadToEnd();
        }
    }
}
 
//-----------------
//最後印出字串 "text to be encrypted"
System.Console.WriteLine(plaintext);

iOS App 在背景狀態下持續更新 GPS 回報之位置

一般 App 在進入 Background 背景狀態之後就會被暫停執行,但做以下設定之後 App 可在此狀態持續更新 GPS 回報的使用者座標位置 :

1. 在 App 的 Info.plist 檔案的 Required device capabilities 項目底下加入 location-services 及 gps
2. 同樣在該檔案的 Required background modes 底下加入 App registers for location updates

設定 Info.plist 檔案之 Required device capabilities 及 Required background modes

接下來的範例是開一個 empty iOS Application project 然後加入一些程式碼來測試 :

1. 為 project 加入 CoreLocation.framework

加入 CoreLocation.framework 至 Linked Frameworks and framework

2. 在 AppDelegate.h 檔案增加 / 修改程式碼  :
#import <CoreLocation/CoreLocation.h>
@interface AppDelegate : UIResponder <UIApplicationDelegate, CLLocationManagerDelegate>
3. 在 AppDelegate.cpp 檔案增加程式碼 :
CLLocationManager* locationManager =nil;
- (void)startStandardUpdates
{
    if (nil == locationManager)
        locationManager = [[CLLocationManager alloc] init];
    
    locationManager.delegate = self;
    locationManager.desiredAccuracy = kCLLocationAccuracyBest;
    locationManager.distanceFilter = kCLDistanceFilterNone;
    [locationManager startUpdatingLocation];
}

-(void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error
{
    NSLog(@"update location err-\n%@", error);
}

// Delegate method from the CLLocationManagerDelegate protocol.
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations
{
    CLLocation* location = [locations lastObject];
    NSString* pp =[NSString stringWithFormat:@"http://192.168.11.6:10001/?lat=%.3f&lon=%.3f", location.coordinate.latitude, location.coordinate.longitude];
    
    NSURL* response =[NSURL URLWithString:pp];
    NSString* response_str =[NSString stringWithContentsOfURL:response encoding:NSUTF8StringEncoding error:nil];
    NSLog(@"%@, response of report=%@", pp, response_str);
}

函數 didUpdateLocations 在每次更新 GPS 回報的位置時使用 NSURL 以 http 方式向伺服器 192.168.11.6 以 GET 方式回報位置 (lat, lon)。

4. 在 AppDelegate.cpp 檔案之函數 didFinishLaunchingWithOptions 內加入程式碼 :
[self startStandardUpdates];
在程式啟動時呼叫 startStandardUpdates 開始取得 GPS 回報的使用者位置。