如何从网站使用GnuPG / GPG4Win加密/解密?

时间:2011-09-28 22:34:58

标签: asp.net encryption gnupg

我正在尝试使用gpg4win 2.1.0加密/解密用户名以在两个不同的网站之间传递。我可以让我的代码在我的开发机器上运行,但不能在生产中运行。

我正在使用VS 2008开发应用程序。

我已经运行了GPG4Win安装包,选择了gnupg&克列奥帕特拉。

我试图使用“http://www.codeproject.com/KB/security/gnupgdotnet.aspx”中的代码。

我一直收到错误代码255未知错误。

以下代码示例是GPG应用程序的运行方式。 BuildOptions()函数返回字符串:

--homedir "C:\Path\gnupg" --no-auto-check-trustdb --always-trust --no-default-keyring --secret-keyring "C:\Path\gnupg\secring.gpg" --keyring "C:\Path\gnupg\pubring.gpg" --yes --batch --encrypt --armor --recipient recipient@email.ca --passphrase-fd 0 --no-verbose

public void ExecuteCommand(string inputText, out string outputText)
{
  outputText = "";

  string gpgOptions = BuildOptions();
  string gpgExecutable = GetGpgPath();
  binddirectory = GetGPGInstallLocation();

  // TODO check existence of _bindirectory and gpgExecutable

  // Create startinfo object

  ProcessStartInfo pInfo = new ProcessStartInfo(gpgExecutable, gpgOptions);
  pInfo.WorkingDirectory = _bindirectory;
  pInfo.CreateNoWindow = true;
  pInfo.UseShellExecute = false;
  // Redirect everything: 
  // stdin to send the passphrase, stdout to get encrypted message, stderr in case of errors...
  pInfo.RedirectStandardInput = true;
  pInfo.RedirectStandardOutput = true;
  pInfo.RedirectStandardError = true;
  _processObject = Process.Start(pInfo);

  // Send pass phrase, if any
  if (!string.IsNullOrEmpty(_passphrase))
  {
    _processObject.StandardInput.WriteLine(_passphrase);
    _processObject.StandardInput.Flush();
  }

  // Send input text
  _processObject.StandardInput.Write(inputText);
  _processObject.StandardInput.Flush();
  _processObject.StandardInput.Close();

  _outputString = "";
  _errorString = "";

  // Create two threads to read both output/error streams without creating a deadlock
  ThreadStart outputEntry = new ThreadStart(StandardOutputReader);
  Thread outputThread = new Thread(outputEntry);
  outputThread.Start();
  ThreadStart errorEntry = new ThreadStart(StandardErrorReader);
  Thread errorThread = new Thread(errorEntry);
  errorThread.Start();

  if (_processObject.WaitForExit(ProcessTimeOutMilliseconds))
  {
     // Process exited before timeout...
     // Wait for the threads to complete reading output/error (but use a timeout!)
     if (!outputThread.Join(ProcessTimeOutMilliseconds/2))
       outputThread.Abort();

     if (!errorThread.Join(ProcessTimeOutMilliseconds/2))
       errorThread.Abort();
  }
  else
  {
    // Process timeout: PGP hung somewhere... kill it (as well as the threads!)
    _outputString = "";
    _errorString = "Timed out after " + ProcessTimeOutMilliseconds.ToString() + " milliseconds";
    _processObject.Kill();
    if (outputThread.IsAlive)
      outputThread.Abort();

    if (errorThread.IsAlive)
      errorThread.Abort();
  }

  // Check results and prepare output
  _exitcode = _processObject.ExitCode;
  if (_exitcode == 0)
    outputText = _outputString;
  else
  {
    if (_errorString == "")
    {
      _errorString = "GPGNET: [" + _processObject.ExitCode.ToString() + "]: Unknown error";
    }
    throw new GnuPGException(_errorString);
  }
}

2 个答案:

答案 0 :(得分:0)

我能够通过创建用户运行的应用程序池标识来解决我的问题,并设置访问密钥环/ gpg程序所需的权限。

答案 1 :(得分:0)

我在Windows服务应用程序中使用此代码。用于文件传输加密和解密

但是如果inputText大小大于~180 KB

 _processObject.StandardInput.Write(inputText);

此行已锁定我的服务。

我不明白这种状态。请帮忙!!!